A blog about Code, the Web and Cyberculture. //martin-thoma.com/ A blog about Code, the Web and Cyberculture. And a bit about math. And some personal bits. en-us Mon, 01 Feb 2016 17:25:47 +0100 Mon, 01 Feb 2016 17:25:47 +0100 Comparing Classifiers //martin-thoma.com/comparing-classifiers/ Tue, 19 Jan 2016 20:13:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/comparing-classifiers <p>Classification problems occur quite often and many different classification algorithms have been described and implemented. But what is the best algorithm for a given error function and dataset?</p> <p>I read questions like “I have problem X. What is the best classifier?” quite often and my first impulse is always to write: Just try them!</p> <p>I guess people asking this question might think that it is super difficult to do so. However, the sklearn tutorial contains a very nice example where many classifiers are compared (<a href="http://scikit-learn.org/stable/auto_examples/classification/plot_classifier_comparison.html">source</a>).</p> <p>This article gives you an overview over some classifiers:</p> <ul> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.svm.SVC.html">SVM</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.neighbors.KNeighborsClassifier.html">k-nearest neighbors</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.ensemble.RandomForestClassifier.html">Random Forest</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.ensemble.AdaBoostClassifier.html">AdaBoost Classifier</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.ensemble.GradientBoostingClassifier.html">Gradient Boosting</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.naive_bayes.GaussianNB.html">Naive Bayes</a></li> <li><a href="http://scikit-learn.org/0.16/modules/generated/sklearn.lda.LDA.html">LDA</a></li> <li><a href="http://scikit-learn.org/0.16/modules/generated/sklearn.qda.QDA.html">QDA</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.neural_network.BernoulliRBM.html">RBMs</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.linear_model.LogisticRegression.html">Logistic Regression</a></li> <li><a href="http://scikit-learn.org/stable/modules/generated/sklearn.neural_network.BernoulliRBM.html">RBM</a> + Logistic Regression Classifier</li> </ul> <p>Of course, neural networks are also one very powerful ML classifier I may not forget. As sklearn does not have neural networks, I’ve installed <a href="https://github.com/tensorflow/skflow"><code>skflow</code></a>.</p> <h2 id="tutorial-example">Tutorial example</h2> <p>The sklearn tutorial creates three datasets with 100 points per dataset and 2 dimensions per point:</p> <ol> <li><strong>Moons</strong>: Two interleaving half-circles</li> <li><strong>Circles</strong>: A larger circle containing the smaller one</li> <li><strong>Linear</strong>: A linearly seperable dataset</li> </ol> <p>Each of those three datasets has added noise. This means for some points there might be no way of classifying them correclty.</p> <p>Here are the results</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/ml-classifiers-1.png"><img src="//martin-thoma.com/captions/ml-classifiers-1.png" alt="k nearest neighbors, linear and RBFSVM" width="500" height="357" class="" /></a><p class="wp-caption-text">k nearest neighbors, linear and RBFSVM</p></div> <p>One can see that k nearest neighbors gives arbitrary decision boundaries. Overall, they look reasonable. However, there are often strange zig-zag patterns.</p> <p>The linear SVM in contrast has a very easy decision boundary: a line. It is no suprise that it can’t deal with the moons dataset. Note that a random guess would be right in 50% of the cases.</p> <p>The RBF SVM has very nice decision boundary. It is smooth, matches the pattern and is able to adjust to all three examles.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/ml-classifiers-2.png"><img src="//martin-thoma.com/captions/ml-classifiers-2.png" alt="Decision Tree, Random Forest, AdaBoost" width="500" height="363" class="" /></a><p class="wp-caption-text">Decision Tree, Random Forest, AdaBoost</p></div> <p>Decision Trees, Decision Forests and AdaBoost all show very similar patterns. The boundaries change in parallel to the coordinate axes which looks very unnatural.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/ml-classifiers-3.png"><img src="//martin-thoma.com/captions/ml-classifiers-3.png" alt="Naive Bayes, LDA, QDA" width="500" height="342" class="" /></a><p class="wp-caption-text">Naive Bayes, LDA, QDA</p></div> <p>Naive Bayes shows nice, smooth patterns. However, those patterns seem to be a bit too simple. LDA is again linear (see linear SVM). Comparing QDA to Naive Bayes is interesting. Although they get similar performance for the first dataset, I would argue that the naive bayes classifier is much better as it is much more confident for its classification. Even more extrem is the last example. I’m astonished that the QDA gets 93% with that boundary; Naive Bayes seems to find a much better boundary.</p> <h2 id="the-hardware">The hardware</h2> <p>The following comparison is done on a PC with an <a href="http://ark.intel.com/de/products/77781/Intel-Core-i7-4820K-Processor-10M-Cache-up-to-3_90-GHz">Intel i7-4820K CPU</a> and a NVIDIA GeForce GTX Titan Black GPU.</p> <h2 id="mnist">MNIST</h2> <p>MNIST is a dataset of <span>\(28\text{px} \times 28\text{px}\)</span> greyscale images. Each of the images contains a digit (0, 1, 2, 3, 4, 5, 6, 7, 8, 9). The task is to classify the image into one of the 10 digit classes.</p> <p>Guessing randomly will give an accuracy of <span>\(\frac{1}{10} = 0.1\)</span>.</p> <h3 id="neural-networks">Neural Networks</h3> <p>Please note that there are neural networks which get much better accuracy. Most notably the <a href="https://www.tensorflow.org/versions/master/tutorials/mnist/pros/index.html#deep-mnist-for-experts">MNIST Expert tutorial</a> with 99.2% accuracy.</p> <h4 id="simple-network">Simple Network</h4> <pre><code>Classifier: NN 500:200 Training time: 79.5696s Testing time: 0.3480s Confusion matrix: [[2248 1 5 1 2 4 8 2 5 2] [ 1 2565 10 1 1 0 2 7 1 0] [ 7 2 2258 14 5 0 9 6 10 3] [ 0 0 12 2294 0 23 0 6 3 10] [ 0 3 3 0 2161 0 8 5 1 30] [ 4 1 1 16 1 2014 17 1 5 9] [ 11 7 1 0 5 6 2237 0 4 0] [ 3 6 14 7 3 1 0 2355 10 18] [ 3 7 3 14 2 17 4 1 2161 3] [ 4 4 0 4 16 8 0 7 6 2340]] Accuracy: 0.9798 </code></pre> <h4 id="dropout-network">Dropout Network</h4> <pre><code>Classifier: NN 500:200 dropout Training time: 118.2654s Testing time: 0.3918s Confusion matrix: [[2250 1 7 1 1 1 5 4 4 4] [ 1 2567 9 1 1 0 0 3 5 1] [ 6 6 2272 3 2 1 3 10 8 3] [ 0 0 26 2260 0 24 0 10 19 9] [ 0 3 5 0 2152 0 7 3 1 40] [ 8 3 3 12 2 1983 20 6 21 11] [ 11 6 3 0 7 1 2237 0 6 0] [ 2 7 13 3 11 0 1 2363 5 12] [ 7 7 9 5 3 3 1 2 2170 8] [ 3 3 1 3 13 2 0 19 8 2337]] Accuracy: 0.9780 </code></pre> <h4 id="cnn">CNN</h4> <pre><code>Classifier: CNN Training time: 391.8810s Testing time: 1.2035s Confusion matrix: [[2243 0 5 0 0 5 9 1 12 3] [ 1 2548 20 4 2 0 1 6 6 0] [ 3 8 2253 9 3 1 4 17 14 2] [ 0 4 13 2290 0 12 0 9 11 9] [ 2 4 5 0 2164 0 8 5 3 20] [ 6 2 3 15 0 2016 9 3 9 6] [ 12 12 1 1 6 6 2227 0 6 0] [ 3 4 11 3 4 1 0 2374 4 13] [ 3 15 6 13 4 11 3 8 2145 7] [ 6 5 0 11 16 8 0 24 13 2306]] Accuracy: 0.9769 </code></pre> <h3 id="svm">SVM</h3> <p>There is a ton of literature / papers about <abbr title="Support Vector Machines">SVMs</abbr>. I’ve summed up the basics on <a href="https://martin-thoma.com/svm-with-sklearn/">Using SVMs with sklearn</a>.</p> <p>I’ve trained two SVMs: A simple, linear one and one with an RBF kernel as I found it online (I’m sorry, I don’t remember where I found those parameters :-/).</p> <p>Please note the the SVM implementation of sklearn does not use the GPU. However, there are <a href="http://fastml.com/running-things-on-a-gpu/">GPU implmentations of SVMs</a> around.</p> <h4 id="linear-svm">Linear SVM</h4> <pre><code>Classifier: linear SVM Training time: 168.6950s Testing time: 158.0101s Confusion matrix: [[2226 0 9 2 6 12 8 3 11 1] [ 1 2537 18 3 3 1 1 7 17 0] [ 12 16 2158 25 24 6 27 19 25 2] [ 3 7 46 2188 4 47 3 18 27 5] [ 2 5 19 1 2117 1 8 6 3 49] [ 18 13 11 73 20 1872 31 0 26 5] [ 20 6 22 1 10 30 2179 0 3 0] [ 5 10 32 11 30 5 0 2268 5 51] [ 11 39 26 47 10 40 7 7 2018 10] [ 11 9 9 24 64 8 0 61 14 2189]] Accuracy: 0.9416 </code></pre> <h4 id="adjusted-svm">Adjusted SVM</h4> <pre><code>Classifier: adj. SVM Training time: 347.1539s Testing time: 234.5724s Confusion matrix: [[2258 1 4 1 2 2 3 1 4 2] [ 1 2566 9 1 1 0 0 7 3 0] [ 4 1 2280 5 4 0 1 9 8 2] [ 0 0 14 2304 1 13 0 6 8 2] [ 2 2 2 0 2183 0 7 5 0 10] [ 4 0 0 16 3 2026 12 1 4 3] [ 7 5 3 0 5 2 2245 0 4 0] [ 1 6 11 2 5 1 0 2373 5 13] [ 3 9 4 9 4 10 2 3 2166 5] [ 3 2 2 6 19 6 0 12 10 2329]] Accuracy: 0.9840 </code></pre> <h3 id="random-forest">Random Forest</h3> <p>Data:</p> <ul> <li><code>n_estimators=50</code></li> <li><code>n_jobs=10</code></li> </ul> <pre><code>Classifier: Random Forest Training time: 2.1359s Testing time: 26.0763s Confusion matrix: [[2246 1 4 1 4 2 7 2 11 0] [ 1 2543 18 5 5 2 3 7 4 0] [ 7 2 2233 20 9 2 9 16 14 2] [ 0 3 36 2240 0 20 3 16 19 11] [ 3 1 5 0 2142 1 11 3 7 38] [ 7 4 4 30 6 1977 16 3 14 8] [ 13 11 4 0 10 15 2210 0 8 0] [ 3 8 29 2 19 0 0 2315 7 34] [ 3 12 18 17 9 26 4 7 2103 16] [ 10 6 6 24 27 13 3 20 18 2262]] Accuracy: 0.9641 </code></pre> <p>Alternatively:</p> <ul> <li><code>max_depth=5</code></li> <li><code>n_estimators=10</code></li> <li><code>max_features=1</code></li> </ul> <pre><code>Classifier: Random Forest 2 Training time: 0.2077s Testing time: 22.2770s Confusion matrix: [[1955 32 63 64 12 4 109 21 13 5] [ 1 2524 20 14 1 6 10 6 6 0] [ 252 425 1198 151 64 1 145 15 55 8] [ 136 195 140 1641 28 11 22 95 65 15] [ 92 320 21 45 1199 9 76 153 8 288] [ 312 383 67 655 78 268 47 94 134 31] [ 199 364 125 58 96 13 1408 5 2 1] [ 83 424 10 70 101 1 19 1555 56 98] [ 392 574 44 147 52 17 71 106 773 39] [ 71 338 11 43 579 2 8 632 24 681]] Accuracy: 0.5715 </code></pre> <h3 id="k-nearest-neightbors">k nearest neightbors</h3> <pre><code>Classifier: k nn Training time: 4.6439s Testing time: 1261.7815s Confusion matrix: [[2260 1 4 0 0 1 6 2 2 2] [ 0 2572 5 0 0 0 1 8 1 1] [ 16 15 2235 9 1 0 5 26 5 2] [ 2 5 14 2276 0 27 1 8 9 6] [ 4 19 0 0 2131 0 8 4 0 45] [ 10 5 3 28 5 1977 25 2 4 10] [ 12 9 0 0 4 7 2239 0 0 0] [ 1 18 4 1 12 0 0 2349 3 29] [ 11 32 8 36 11 34 5 7 2053 18] [ 6 8 4 14 26 4 0 19 5 2303]] Accuracy: 0.9695 </code></pre> <h3 id="decision-tree">Decision Tree</h3> <p>Data:</p> <ul> <li><code>max_depth=5</code></li> </ul> <pre><code>Classifier: Decision Tree Training time: 3.1346s Testing time: 0.0313s Confusion matrix: [[1767 0 11 25 12 120 137 71 114 21] [ 1 2065 128 108 13 17 41 66 131 18] [ 42 44 1248 37 121 21 227 76 339 159] [ 33 22 32 1484 33 107 52 81 266 238] [ 0 15 45 33 1284 42 42 45 213 492] [ 42 10 21 229 166 577 137 123 254 510] [ 34 33 66 24 103 65 1734 24 102 86] [ 10 14 179 57 53 21 19 1775 79 210] [ 1 98 129 43 43 42 160 29 1439 231] [ 4 8 86 59 125 95 36 75 167 1734]] Accuracy: 0.6540 </code></pre> <h3 id="adaboost">Adaboost</h3> <p>You should note that you can use arbitrary base classifiers with Adaboost. The default ones of <a href="http://scikit-learn.org/stable/modules/generated/sklearn.ensemble.AdaBoostClassifier.html"><code>sklearn.ensemble.AdaBoostClassifier</code></a> is <a href="http://scikit-learn.org/stable/modules/generated/sklearn.tree.DecisionTreeClassifier.html"><code>sklearn.tree.DecisionTreeClassifies</code></a></p> <pre><code>Classifier: AdaBoost Training time: 37.6443s Testing time: 1.5815s Confusion matrix: [[1994 0 75 8 6 113 51 3 15 13] [ 0 2435 27 22 2 10 12 37 42 1] [ 97 39 1341 85 39 38 416 39 196 24] [ 108 52 37 1508 13 313 66 64 122 65] [ 11 16 48 23 1662 49 23 134 90 155] [ 81 56 30 309 51 1255 57 17 129 84] [ 29 28 151 7 80 43 1914 2 17 0] [ 25 37 33 36 70 30 0 1761 37 388] [ 30 80 48 215 16 85 30 19 1615 77] [ 13 29 68 66 356 74 1 171 78 1533]] Accuracy: 0.7367 </code></pre> <h3 id="gradient-boosting">Gradient Boosting</h3> <p>Gradient boosting with <code>xgboost</code> has won in the Rossmann Store Sales prediction (<a href="http://blog.kaggle.com/2015/12/21/rossmann-store-sales-winners-interview-1st-place-gert/">source</a>).</p> <p>See also:</p> <ul> <li><a href="http://blog.kaggle.com/2015/09/22/caterpillar-winners-interview-1st-place-gilberto-josef-leustagos-mario/">Caterpillar Winners’ Interview</a></li> <li><a href="http://blog.kaggle.com/2015/10/20/caterpillar-winners-interview-3rd-place-team-shift-workers/">Caterpillar Winners’ Interview: 3rd place</a></li> <li><a href="http://blog.kaggle.com/2015/09/28/liberty-mutual-property-inspection-winners-interview-qingchen-wang/">Liberty Mutual Property Inspection, Winner’s Interview</a></li> <li><a href="http://blog.kaggle.com/2015/10/21/recruit-coupon-purchase-winners-interview-2nd-place-halla-yang/">Recruit Coupon Purchase Winner’s Interview: 2nd place</a></li> <li><a href="http://blog.kaggle.com/2015/10/30/dato-winners-interview-2nd-place-mortehu/">Dato Truly Native? Winner’s Interview: 2nd place</a></li> </ul> <pre><code>Classifier: Gradient Boosting Training time: 2409.8094s Testing time: 0.4159s Confusion matrix: [[2214 1 3 5 10 8 9 3 24 1] [ 1 2528 16 11 3 5 5 7 9 3] [ 8 5 2165 34 16 5 12 22 37 10] [ 1 9 27 2182 4 42 1 22 37 23] [ 5 4 16 1 2088 5 12 5 10 65] [ 9 6 7 41 8 1928 27 6 18 19] [ 15 7 4 1 19 29 2181 1 14 0] [ 6 16 27 15 22 6 0 2246 8 71] [ 5 20 14 25 15 29 6 6 2057 38] [ 6 10 8 24 49 15 1 54 17 2205]] Accuracy: 0.9435 </code></pre> <h3 id="naive-bayes">Naive Bayes</h3> <pre><code>Classifier: Naive Bayes Training time: 0.3814s Testing time: 0.8863s Confusion matrix: [[2094 4 11 10 6 7 56 3 69 18] [ 4 2432 9 11 2 4 28 1 77 20] [ 278 64 703 143 6 4 558 4 528 26] [ 202 136 18 791 5 5 106 21 886 178] [ 96 26 16 14 296 8 169 13 535 1038] [ 327 63 15 39 14 87 100 5 1253 166] [ 34 51 17 1 1 5 2109 0 52 1] [ 19 21 3 23 20 2 7 737 123 1462] [ 39 326 13 16 8 18 25 7 1482 281] [ 15 26 8 2 14 2 1 41 40 2240]] Accuracy: 0.5615 </code></pre> <h3 id="lda">LDA</h3> <pre><code>Classifier: LDA Training time: 20.6464s Testing time: 0.0910s Confusion matrix: [[2131 2 10 14 12 47 20 4 36 2] [ 0 2454 20 10 5 16 5 5 71 2] [ 22 71 1873 77 51 8 82 20 101 9] [ 5 32 56 1992 11 77 11 40 80 44] [ 1 21 17 0 1983 12 12 2 21 142] [ 19 18 11 112 18 1682 37 11 103 58] [ 28 30 32 3 43 51 2046 0 37 1] [ 16 57 25 20 70 8 0 1990 11 220] [ 9 113 16 64 33 115 13 10 1781 61] [ 15 10 6 35 133 14 0 122 22 2032]] Accuracy: 0.8642 </code></pre> <h3 id="qda">QDA</h3> <pre><code>Classifier: QDA Training time: 23.0527s Testing time: 6.2259s Confusion matrix: [[2212 3 12 14 1 4 20 5 6 1] [ 66 2409 12 10 0 0 32 2 39 18] [ 961 25 689 143 3 1 310 2 166 14] [1231 48 29 606 3 13 66 10 232 110] [ 810 22 25 27 250 4 143 17 345 568] [ 909 15 13 33 1 214 140 4 666 74] [ 83 18 14 1 1 2 2146 0 6 0] [ 81 13 6 52 14 2 1 776 120 1352] [ 487 181 18 20 6 17 58 3 1320 105] [ 65 14 12 7 10 0 0 23 33 2225]] Accuracy: 0.5561 </code></pre> <h2 id="mnist-summary">MNIST Summary</h2> <table class="table"> <thead> <tr> <th>Classifier</th> <th>Accuracy</th> <th>Training Time</th> <th>Testing Time</th> </tr> </thead> <tbody> <tr> <td>MLP (500:200)</td> <td style="text-align: right">97.98%</td> <td style="text-align: right">79.5696s</td> <td style="text-align: right">0.3480s</td> </tr> <tr> <td>Dropout NN (500:200)</td> <td style="text-align: right">97.80%</td> <td style="text-align: right">118.2654s</td> <td style="text-align: right">0.3918s</td> </tr> <tr> <td>CNN<br />(32 5&times;5 filters : 2&times;2 max pool : 64 5&times;5 filters : 2&times;2 max pool : 1024)</td> <td style="text-align: right">97.69%</td> <td style="text-align: right">391.8810s</td> <td style="text-align: right">1.2035s</td> </tr> <tr> <td>Adjusted SVM</td> <td style="text-align: right"><b>98.40%</b></td> <td style="text-align: right">347.1539s</td> <td style="text-align: right" class="danger">234.5724s</td> </tr> <tr> <td>Linear SVM</td> <td style="text-align: right">94.16%</td> <td style="text-align: right">168.6950s</td> <td style="text-align: right" class="danger">158.0101s</td> </tr> <tr> <td>Random Forest (n_estimators=50, n_jobs=10)</td> <td style="text-align: right">96.41%</td> <td style="text-align: right">2.1359s</td> <td style="text-align: right" class="danger">26.0763s</td> </tr> <tr> <td>Random Forest (n_estimators=10, max_features=1, max_depth=5)</td> <td style="text-align: right" class="danger">57.15%</td> <td style="text-align: right"><b>0.2077s</b></td> <td style="text-align: right" class="danger">22.2770s</td> </tr> <tr> <td>k nearest neightbors (k=3)</td> <td style="text-align: right">96.95%</td> <td style="text-align: right">4.6439s</td> <td style="text-align: right" class="danger">1261.7815s</td> </tr> <tr> <td>Decision Tree(max_depth=5)</td> <td style="text-align: right" class="danger">65.40%</td> <td style="text-align: right">3.1346s</td> <td style="text-align: right"><b>0.0313s</b></td> </tr> <tr> <td>Adaboost</td> <td style="text-align: right" class="danger">73.67%</td> <td style="text-align: right">37.6443s</td> <td style="text-align: right">1.5815s</td> </tr> <tr> <td>Naive Bayes</td> <td style="text-align: right" class="danger">56.15%</td> <td style="text-align: right">0.3814s</td> <td style="text-align: right">0.8863s</td> </tr> <tr> <td>LDA</td> <td style="text-align: right">86.42%</td> <td style="text-align: right">20.6464s</td> <td style="text-align: right">0.0910s</td> </tr> <tr> <td>QDA</td> <td style="text-align: right" class="danger">55.61%</td> <td style="text-align: right">23.0527s</td> <td style="text-align: right" class="danger">6.2259s</td> </tr> <tr> <td>Gradient Boosting</td> <td style="text-align: right">94.35%</td> <td style="text-align: right">2409.8094s</td> <td style="text-align: right">0.4159s</td> </tr> <tr> <td>Logistic Regression (C=1)</td> <td style="text-align: right">91.47%</td> <td style="text-align: right">272.1309s</td> <td style="text-align: right">0.0531s</td> </tr> <tr> <td>Logistic Regression (C=10000)</td> <td style="text-align: right">91.23%</td> <td style="text-align: right">1807.0624s</td> <td style="text-align: right">0.0529s</td> </tr> </tbody> </table> <h2 id="iris-summary">IRIS summary</h2> <p>Just for fun, I tried the script from above with very minor adjustments to the <a href="https://en.wikipedia.org/wiki/Iris_flower_data_set">IRIS flower dataset</a>:</p> <table class="table"> <thead> <tr> <th>Classifier</th> <th>Accuracy</th> <th>Training Time</th> <th>Testing Time</th> </tr> </thead> <tbody> <tr> <td>AdaBoost</td> <td style="text-align: right">92.00%</td> <td style="text-align: right">0.1203s</td> <td style="text-align: right">0.0101s</td> </tr> <tr> <td>Decision Tree</td> <td style="text-align: right">92.00%</td> <td style="text-align: right">0.0005s</td> <td style="text-align: right"><b>0.0001s</b></td> </tr> <tr> <td>Gradient Boosting</td> <td style="text-align: right">92.00%</td> <td style="text-align: right">0.2227s</td> <td style="text-align: right">0.0007s</td> </tr> <tr> <td>LDA</td> <td style="text-align: right"><b>96.00%</b></td> <td style="text-align: right">0.0027s</td> <td style="text-align: right">0.0002s</td> </tr> <tr> <td>NN 20:5</td> <td style="text-align: right">90.00%</td> <td style="text-align: right">1.6628s</td> <td style="text-align: right">0.0046s</td> </tr> <tr> <td>Naive Bayes</td> <td style="text-align: right">90.00%</td> <td style="text-align: right">0.0010s</td> <td style="text-align: right">0.0004s</td> </tr> <tr> <td>QDA</td> <td style="text-align: right">94.00%</td> <td style="text-align: right">0.0009s</td> <td style="text-align: right">0.0003s</td> </tr> <tr> <td>Random Forest</td> <td style="text-align: right">90.00%</td> <td style="text-align: right">0.2147s</td> <td style="text-align: right">0.1395s</td> </tr> <tr> <td>Random Forest 2</td> <td style="text-align: right">90.00%</td> <td style="text-align: right">0.1481s</td> <td style="text-align: right">0.1249s</td> </tr> <tr> <td>SVM, adj.</td> <td style="text-align: right">90.00%</td> <td style="text-align: right">0.0010s</td> <td style="text-align: right">0.0004s</td> </tr> <tr> <td>SVM, linear</td> <td style="text-align: right" class="danger">88.00%</td> <td style="text-align: right">0.0006s</td> <td style="text-align: right">0.0002s</td> </tr> <tr> <td>k nn</td> <td style="text-align: right">92.00%</td> <td style="text-align: right">0.0007s</td> <td style="text-align: right">0.0009s</td> </tr> <tr> <td>Logistic Regression (C=1)</td> <td style="text-align: right" class="danger">88.00%</td> <td style="text-align: right">0.0011s</td> <td style="text-align: right"><b>0.0001s</b></td> </tr> <tr> <td>Logistic Regression (C=1000)</td> <td style="text-align: right">92.00%</td> <td style="text-align: right">0.0010s</td> <td style="text-align: right">0.0002s</td> </tr> <tr> <td>RBM 100</td> <td style="text-align: right" class="danger">78.00%</td> <td style="text-align: right">0.0233s</td> <td style="text-align: right">0.0003s</td> </tr> <tr> <td>RBM 100, n_iter=20</td> <td style="text-align: right" class="danger">70.00%</td> <td style="text-align: right">0.0427s</td> <td style="text-align: right">0.0003s</td> </tr> <tr> <td>RBM 200, n_iter=40, LR=0.01, Reg: C=1</td> <td style="text-align: right" class="danger">88.00%</td> <td style="text-align: right">0.2463s</td> <td style="text-align: right">0.0005s</td> </tr> <tr> <td>RBM 200, n_iter=40, LR=0.01, Reg: C=10000</td> <td style="text-align: right">90.00%</td> <td style="text-align: right">0.2437s</td> <td style="text-align: right">0.0005s</td> </tr> <tr> <td>RBM 256</td> <td style="text-align: right" class="danger">84.00%</td> <td style="text-align: right">0.0424s</td> <td style="text-align: right">0.0006s</td> </tr> <tr> <td>RBM 512, n_iter=100</td> <td style="text-align: right" class="danger">84.00%</td> <td style="text-align: right">0.0723s</td> <td style="text-align: right">0.0010s</td> </tr> </tbody> </table> <h2 id="tldr">TL;DR</h2> <p>Neural networks take their time to train and a feeling for the topology, but their classification results are nice and the testing time is good as well.</p> <p>Random Forests and SVMs are also a model a type of model one should think of. However, the stard implementation is very slow compared to neural networks.</p> <p><a href="http://scikit-learn.org/0.16/modules/generated/sklearn.lda.LDA.html"><code>sklearn.lda.LDA</code></a> might also be worth a try. The rest seems to be quite bad compared with those classifiers.</p> <p>The code which generated the examples from above is <a href="https://github.com/MartinThoma/algorithms/tree/master/ML/mnist/many-classifiers">here</a>.</p> Function Approximation //martin-thoma.com/function-approximation/ Mon, 18 Jan 2016 20:00:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/function-approximation <p>I was recently quite disappointed by how bad neural networks are for function approximation (see <a href="http://datascience.stackexchange.com/q/9495/8820">How should a neural network for unbound function approximation be structured?</a>). However, I’ve just found that Gaussian processes are great for function approximation!</p> <p>There are two important types of function approximation:</p> <ul> <li><strong>Interpolation</strong>: What values does the function have in between of known values?</li> <li><strong>Extrapolation</strong>: What values does the function have outsive of the known values?</li> </ul> <p>I did a couple of very quick examples which look promising.</p> <h2 id="examples">Examples</h2> <h3 id="square">Square</h3> <p>Approximating \(f(x) = x^2\) worked very good:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/gauss-x2.png"><img src="//martin-thoma.com/captions/gauss-x2.png" alt="f(x) = x^2" width="500" height="377" class="" /></a><p class="wp-caption-text">f(x) = x^2</p></div> <p>I’ve tried if with higher order polynomials, more complex polynomials. No problem.</p> <h3 id="sin">Sin</h3> <p>Approximating \(f(x) = \sin(3x)\) seems to be more complicated:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/gaussian-process-sin-3x.png"><img src="//martin-thoma.com/captions/gaussian-process-sin-3x.png" alt="f(x) = sin(3x)" width="500" height="377" class="" /></a><p class="wp-caption-text">f(x) = sin(3x)</p></div> <p>I guess a human would see the wave pattern and do a better job here.</p> <h3 id="exp">exp</h3> <p>Approximating \(f(x) = e^x\) works similar well as polynomials. One can see that it does not perfectly fit it, but compared the the range of values seen before and the distance from the last seen value I think this is absolutely acceptable:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/gauss-exponential.png"><img src="//martin-thoma.com/captions/gauss-exponential.png" alt="f(x) = e^x" width="500" height="377" class="" /></a><p class="wp-caption-text">f(x) = e^x</p></div> <h3 id="noise">noise</h3> <p>It is claimed that Gaussian processes implicitly model noise so that they can easily deal with noise. However, in my experients this seems not to work so great. The reason might be that I had points in \([-3, 3]\) of the function</p> <p>\[f(x) = x^2\]</p> <p>with point-wise gaussian noise \(N \sim \mathcal{N}(0, 1)\). So the noise is quite domintant on that intervall. One of the examples where it worked better is:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/gauss-noise.png"><img src="//martin-thoma.com/captions/gauss-noise.png" alt="f(x) = x^2 with gaussian noise" width="500" height="251" class="" /></a><p class="wp-caption-text">f(x) = x^2 with gaussian noise</p></div> <h3 id="make-it-brake">Make it brake</h3> <p>I was a bit suspicious if I had another mistake here. So I wanted it to break. This was the reason why I created the following function</p> <p>\[f(x) = \begin{cases}x^2 &amp;\text{if } x \geq 0\\-1 &amp;\text{otherwise}\end{cases}\]</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/gauss-cases.png"><img src="//martin-thoma.com/captions/gauss-cases.png" alt="Function with discontinuity" width="500" height="377" class="" /></a><p class="wp-caption-text">Function with discontinuity</p></div> <p>The predicted value is obviously not correct, but you should note that almost all function values are within the 95% confidence intervall!</p> <h2 id="code">Code</h2> <p>The following code needs <a href="http://docs.scipy.org/doc/numpy-1.10.1/user/install.html"><code>numpy</code></a> and <a href="http://scikit-learn.org/stable/install.html"><code>sklearn</code></a>. For the plots, you need <a href="http://matplotlib.org/users/installing.html"><code>matplotlib</code></a>.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Example how to use gaussion processes for regression.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">as</span> np <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">gaussian_process</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">main</span>(): <span style="color:#777"># Create the dataset</span> x_train = np.atleast_2d(np.linspace(-<span style="color:#00D">3</span>, <span style="color:#00D">3</span>, num=<span style="color:#00D">50</span>)).T y_train = f(x_train).ravel() x_test = np.atleast_2d(np.linspace(-<span style="color:#00D">5</span>, <span style="color:#00D">5</span>, <span style="color:#00D">1000</span>)).T <span style="color:#777"># Define the Regression Modell and fit it</span> gp = gaussian_process.GaussianProcess(theta0=<span style="color:#60E">1e-2</span>, thetaL=<span style="color:#60E">1e-4</span>, thetaU=<span style="color:#60E">1e-3</span>) gp.fit(x_train, y_train) <span style="color:#777"># Evaluate the result</span> y_pred, mse = gp.predict(x_test, eval_MSE=<span style="color:#069">True</span>) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">MSE: %0.4f</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">sum</span>(mse)) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">max MSE: %0.4f</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">max</span>(mse)) plot_graph(x_test, x_train, y_pred, mse, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x^2</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">f</span>(x): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> Function which gets approximated</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> noise = [np.random.normal(loc=<span style="color:#60E">0.0</span>, scale=<span style="color:#60E">1.0</span>) <span style="color:#080;font-weight:bold">for</span> _ <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(<span style="color:#369;font-weight:bold">list</span>(x)))] noise = np.atleast_2d(noise).T <span style="color:#080;font-weight:bold">return</span> x**<span style="color:#00D">2</span> + noise <span style="color:#777"># Totally fails for that one:</span> <span style="color:#777"># y = []</span> <span style="color:#777"># for el in x:</span> <span style="color:#777"># if el &gt;= 0:</span> <span style="color:#777"># y.append(el**2)</span> <span style="color:#777"># else:</span> <span style="color:#777"># y.append(-1)</span> <span style="color:#777"># return np.array(y)</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">plot_graph</span>(x, x_train, y_pred, mse, function_tex): <span style="color:#777"># Plot the function, the prediction and the 95% confidence interval</span> <span style="color:#777"># based on the MSE</span> sigma = np.sqrt(mse) <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">matplotlib</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">pyplot</span> <span style="color:#080;font-weight:bold">as</span> pl pl.figure() y = f(x_train).ravel() pl.plot(x, f(x), <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">r:</span><span style="color:#710">'</span></span>, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">$f(x) = %s$</span><span style="color:#710">'</span></span> % function_tex) pl.plot(x_train, y, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">r.</span><span style="color:#710">'</span></span>, markersize=<span style="color:#00D">10</span>, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">Observations</span><span style="color:#710">'</span></span>) pl.plot(x, y_pred, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">b-</span><span style="color:#710">'</span></span>, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">Prediction</span><span style="color:#710">'</span></span>) pl.fill(np.concatenate([x, x[::-<span style="color:#00D">1</span>]]), np.concatenate([y_pred - <span style="color:#60E">1.9600</span> * sigma, (y_pred + <span style="color:#60E">1.9600</span> * sigma)[::-<span style="color:#00D">1</span>]]), alpha=<span style="color:#60E">.5</span>, fc=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">b</span><span style="color:#710">'</span></span>, ec=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">None</span><span style="color:#710">'</span></span>, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">95% confidence interval</span><span style="color:#710">'</span></span>) pl.xlabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">$x$</span><span style="color:#710">'</span></span>) pl.ylabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">$f(x)$</span><span style="color:#710">'</span></span>) y_min = <span style="color:#369;font-weight:bold">min</span>(<span style="color:#369;font-weight:bold">min</span>(y_pred), <span style="color:#369;font-weight:bold">min</span>(y)) * <span style="color:#60E">1.1</span> y_max = <span style="color:#369;font-weight:bold">max</span>(<span style="color:#369;font-weight:bold">max</span>(y_pred), <span style="color:#369;font-weight:bold">max</span>(y)) * <span style="color:#60E">1.1</span> pl.ylim(y_min, y_max) pl.legend(loc=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">upper left</span><span style="color:#710">'</span></span>) pl.show() <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: main() </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li><a href="http://www.gaussianprocess.org/">www.gaussianprocess.org</a>: The definitive book about gaussian processes. It’s freely available online!</li> <li><a href="https://en.wikipedia.org/wiki/Kriging">Wikipedia</a></li> <li>sklearn: <a href="http://scikit-learn.org/stable/modules/gaussian_process.html">Gaussian Processes</a></li> <li>sklearn: <a href="http://scikit-learn.org/stable/auto_examples/gaussian_process/plot_gp_regression.html">Gaussian Processes regression: basic introductory example</a></li> </ul> Using SVMs with sklearn //martin-thoma.com/svm-with-sklearn/ Thu, 14 Jan 2016 12:25:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/svm-with-sklearn <p>Support Vector Machines (SVMs) is a group of powerful classifiers. In this article, I will give a short impression of how they work. I continue with an example how to use SVMs with sklearn.</p> <h2 id="svm-theory">SVM theory</h2> <p><abbr title="Support Vector Machines">SVMs</abbr> can be described with 5 ideas in mind:</p> <ol> <li><b>Linear, binary classifiers</b>: If data is linearly separable, it can be separated by a hyperplane. There is one hyperplane which maximizes the distance to the next datapoints (support vectors). This hyperplane should be taken:<br /> <div> \[ \begin{aligned} \text{minimize}_{\mathbf{w}, b}\,&amp;\frac{1}{2} \|\mathbf{w}\|^2\\ \text{s.t. }&amp; \forall_{i=1}^m y_i \cdot \underbrace{(\langle \mathbf{w}, \mathbf{x}_i\rangle + b)}_{\text{Classification}} \geq 1 \end{aligned}\]</div></li> <li><b>Slack variables</b>: Even if the underlying process which generates the features for the two classes is linearly separable, noise can make the data not separable. The introduction of <i>slack&nbsp;variables</i> to relax the requirement of linear separability solves this problem. The trade-off between accepting some errors and a more complex model is weighted by a parameter \(C \in \mathbb{R}_0^+\). The bigger \(C\), the more errors are accepted. The new optimization problem is: \[ \begin{aligned} \text{minimize}_{\mathbf{w}}\,&amp;\frac{1}{2} \|\mathbf{w}\|^2 + C \cdot \sum_{i=1}^m \xi_i\\ \text{s.t. }&amp; \forall_{i=1}^m y_i \cdot (\langle \mathbf{w}, \mathbf{x}_i\rangle + b) \geq 1 - \xi_i \end{aligned}\] Note that \(0 \le \xi_i \le 1\) means that the data point is within the margin, whereas \(\xi_i \ge 1\) means it is misclassified. An SVM with \(C &gt; 0\) is also called a <i>soft-margin SVM</i>.</li> <li><b>Dual Problem</b>: The primal problem is to find the normal vector \(\mathbf{w}\) and the bias \(b\). The dual problem is to express \(\mathbf{w}\) as a linear combination of the training data \(\mathbf{x}_i\): \[\mathbf{w} = \sum_{i=1}^m \alpha_i y_i \mathbf{x}_i\] where \(y_i \in \{-1, 1\}\) represents the class of the training example and \(\alpha_i\) are Lagrange multipliers. The usage of Lagrange multipliers is explained with some examples in [<a href="#ref-smi04" name="ref-smi04-anchor">Smi04</a>]. The usage of the Lagrange multipliers \(\alpha_i\) changes the optimization problem depend on the \(\alpha_i\) which are weights for the feature vectors. It turns out that most \(\alpha_i\) will be zero. The non-zero weighted vectors are called <i>support&nbsp;vectors</i>. The optimization problem is now, according to [<a href="#ref-bur98" name="ref-bur98-anchor">Bur98</a>] (a great read; if you really want to understand it I can recommend it!): \[ \begin{aligned} \text{maximize}_{\mathbf{w}}\,&amp; \sum_{i=1}^m \alpha_i - \frac{1}{2} \sum_{i=1}^m \sum_{j=1}^m \alpha_i \alpha_j y_i y_j \langle \mathbf{x}_i, \mathbf{x}_j \rangle\\ \text{s.t. } &amp; \forall_{i=1}^m 0 \leq \alpha_i \leq C\\ \text{s.t. } &amp; \sum_{i=1}^m \alpha_i y_i = 0 \end{aligned}\]</li> <li><b>Kernel-Trick</b>: Not every dataset is linearly separable. This problem is approached by transforming the feature vectors \(\mathbf{x}\) with a non-linear mapping \(\Phi\) into a higher dimensional (probably \(\infty\)-dimensional) space. As the feature vectors \(\mathbf{x}\) are only used within scalar product \(\langle \mathbf{x}_i, \mathbf{x}_j \rangle\), it is not necessary to do the transformation. It is enough to do the calculation \[K(\mathbf{x}_i, \mathbf{x}_j) = \langle \mathbf{x}_i, \mathbf{x}_j \rangle\] This function \(K\) is called a <i>kernel</i>. The idea of never explicitly transforming the vectors \(\mathbf{x}_i\) to the higher dimensional space is called the <i>kernel&nbsp;trick</i>. Common kernels include the polynomial kernel \[K_P(\mathbf{x}_i, \mathbf{x}_j) = (\langle \mathbf{x}_i, \mathbf{x}_j \rangle + r)^p\] of degree \(p\) and coefficient \(r\), the Gaussian <abbr title="Radial Basis Function">RBF</abbr> kernel \[K_{\text{Gauss}}(\mathbf{x}_i, \mathbf{x}_j) = e^{\frac{-\gamma\|\mathbf{x}_i - \mathbf{x}_j\|^2}{2 \sigma^2}}\] and the sigmoid kernel \[K_{\text{tanh}}(\mathbf{x}_i, \mathbf{x}_j) = \tanh(\gamma \langle \mathbf{x}_i, \mathbf{x}_j \rangle - r)\] where the parameter \(\gamma\) determines how much influence single training examples have.</li> <li><b>Multiple Classes</b>: By using the <i>one-vs-all</i> or the <i>one-vs-one</i> strategy it is possible to get a classifying system which can distinguish many classes.</li> </ol> <p>A nice visualization of the transformation of the data in a higher-dimensional space was done by</p> <p>TeamGrizzly’s channel: <a href="https://youtu.be/9NrALgHFwTo">Performing nonlinear classification via linear separation in higher dimensional space</a> on YouTube. 22.11.2010.</p> <p>See also:</p> <ul> <li><a href="http://math.stackexchange.com/a/1620256/6876">What is an example of a SVM kernel, where one implicitly uses an infinity-dimensional space?</a></li> <li><a href="http://stackoverflow.com/a/4630731/562769">SVM - hard or soft margins?</a></li> </ul> <h2 id="sklearn">sklearn</h2> <p><code>sklearn</code> is the machine learning toolkit to get started for Python. It has a very good documentation and many functions. You can find <a href="http://scikit-learn.org/stable/install.html">installation instructions</a> on their website.</p> <p>It also includes <a href="http://scikit-learn.org/stable/modules/generated/sklearn.svm.SVC.html#sklearn.svm.SVC"><code>sklearn.svm.SVC</code></a>. SVC is short for <em>support vector classifier</em> and this is how you use it for the MNIST dataset.</p> <p>Parameters for which you might want a further explanation:</p> <ul> <li><code>cache_size</code>: <a href="http://datascience.stackexchange.com/a/996/8820">datascience.stackexchange.com</a></li> </ul> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span>Train a SVM to categorize 28x28 pixel images into digits (MNIST dataset).</span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">as</span> np <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">main</span>(): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Orchestrate the retrival of data, training and testing.</span><span style="color:black">&quot;&quot;&quot;</span></span> data = get_data() <span style="color:#777"># Get classifier</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.svm</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">SVC</span> clf = SVC(probability=<span style="color:#069">False</span>, <span style="color:#777"># cache_size=200,</span> kernel=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">rbf</span><span style="color:#710">&quot;</span></span>, C=<span style="color:#60E">2.8</span>, gamma=<span style="color:#60E">.0073</span>) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Start fitting. This may take a while</span><span style="color:#710">&quot;</span></span>) <span style="color:#777"># take all of it - make that number lower for experiments</span> examples = <span style="color:#369;font-weight:bold">len</span>(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>]) clf.fit(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>][:examples], data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>][:examples]) analyze(clf, data) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">analyze</span>(clf, data): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> Analyze how well a classifier performs on data.</span><span> </span><span> </span><span> Parameters</span><span> </span><span> ----------</span><span> </span><span> clf : classifier object</span><span> </span><span> data : dict</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#777"># Get confusion matrix</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">metrics</span> predicted = clf.predict(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>]) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Confusion matrix:</span><span style="color:#b0b">\n</span><span style="color:#D20">%s</span><span style="color:#710">&quot;</span></span> % metrics.confusion_matrix(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>], predicted)) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Accuracy: %0.4f</span><span style="color:#710">&quot;</span></span> % metrics.accuracy_score(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>], predicted)) <span style="color:#777"># Print example</span> try_id = <span style="color:#00D">1</span> out = clf.predict(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>][try_id]) <span style="color:#777"># clf.predict_proba</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">out: %s</span><span style="color:#710">&quot;</span></span> % out) size = <span style="color:#369;font-weight:bold">int</span>(<span style="color:#369;font-weight:bold">len</span>(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>][try_id])**(<span style="color:#60E">0.5</span>)) view_image(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>][try_id].reshape((size, size)), data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>][try_id]) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">view_image</span>(image, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span>): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> View a single image.</span><span> </span><span> </span><span> Parameters</span><span> </span><span> ----------</span><span> </span><span> image : numpy array</span><span> </span><span> Make sure this is of the shape you want.</span><span> </span><span> label : str</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">matplotlib.pyplot</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">show</span>, <span style="color:#B44;font-weight:bold">imshow</span>, <span style="color:#B44;font-weight:bold">cm</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Label: %s</span><span style="color:#710">&quot;</span></span> % label) imshow(image, cmap=cm.gray) show() <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">get_data</span>(): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> Get data ready to learn with.</span><span> </span><span> </span><span> Returns</span><span> </span><span> -------</span><span> </span><span> dict</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> simple = <span style="color:#069">False</span> <span style="color:#080;font-weight:bold">if</span> simple: <span style="color:#777"># Load the simple, but similar digits dataset</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.datasets</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">load_digits</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.utils</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">shuffle</span> digits = load_digits() x = [np.array(el).flatten() <span style="color:#080;font-weight:bold">for</span> el <span style="color:#080;font-weight:bold">in</span> digits.images] y = digits.target <span style="color:#777"># Scale data to [-1, 1] - This is of mayor importance!!!</span> <span style="color:#777"># In this case, I know the range and thus I can (and should) scale</span> <span style="color:#777"># manually. However, this might not always be the case.</span> <span style="color:#777"># Then try sklearn.preprocessing.MinMaxScaler or</span> <span style="color:#777"># sklearn.preprocessing.StandardScaler</span> x = x/<span style="color:#60E">255.0</span>*<span style="color:#00D">2</span> - <span style="color:#00D">1</span> x, y = shuffle(x, y, random_state=<span style="color:#00D">0</span>) <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.cross_validation</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">train_test_split</span> x_train, x_test, y_train, y_test = train_test_split(x, y, test_size=<span style="color:#60E">0.33</span>, random_state=<span style="color:#00D">42</span>) data = {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train</span><span style="color:#710">'</span></span>: {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>: x_train, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>: y_train}, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>: {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>: x_test, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>: y_test}} <span style="color:#080;font-weight:bold">else</span>: <span style="color:#777"># Load the original dataset</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.datasets</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">fetch_mldata</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.utils</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">shuffle</span> mnist = fetch_mldata(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">MNIST original</span><span style="color:#710">'</span></span>) x = mnist.data y = mnist.target <span style="color:#777"># Scale data to [-1, 1] - This is of mayor importance!!!</span> x = x/<span style="color:#60E">255.0</span>*<span style="color:#00D">2</span> - <span style="color:#00D">1</span> x, y = shuffle(x, y, random_state=<span style="color:#00D">0</span>) <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">sklearn.cross_validation</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">train_test_split</span> x_train, x_test, y_train, y_test = train_test_split(x, y, test_size=<span style="color:#60E">0.33</span>, random_state=<span style="color:#00D">42</span>) data = {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train</span><span style="color:#710">'</span></span>: {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>: x_train, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>: y_train}, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">test</span><span style="color:#710">'</span></span>: {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X</span><span style="color:#710">'</span></span>: x_test, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>: y_test}} <span style="color:#080;font-weight:bold">return</span> data <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: main() </pre></div> </div> </div> <h2 id="results">Results</h2> <p>The script from above gives the following results:</p> <table> <caption>Confusion matrix for an SVM classifier on the MNIST dataset</caption> <thead> <tr> <th></th> <th>0</th> <th>1</th> <th>2</th> <th>3</th> <th>4</th> <th>5</th> <th>6</th> <th>7</th> <th>8</th> <th>9</th> </tr> </thead> <tbody> <tr> <th>0</th> <td>2258</td> <td>1</td> <td>4</td> <td>1</td> <td>2</td> <td>2</td> <td>3</td> <td>1</td> <td>4</td> <td>2</td> </tr> <tr> <th>1</th> <td>1</td> <td>2566</td> <td>9</td> <td>1</td> <td>1</td> <td>0</td> <td>0</td> <td>7</td> <td>3</td> <td>0</td> </tr> <tr> <th>2</th> <td>4</td> <td>1</td> <td>2280</td> <td>5</td> <td>4</td> <td>0</td> <td>1</td> <td>9</td> <td>8</td> <td>2</td> </tr> <tr> <th>3</th> <td>0</td> <td>0</td> <td>14</td> <td>2304</td> <td>1</td> <td>13</td> <td>0</td> <td>6</td> <td>8</td> <td>2</td> </tr> <tr> <th>4</th> <td>2</td> <td>2</td> <td>2</td> <td>0</td> <td>2183</td> <td>0</td> <td>7</td> <td>5</td> <td>0</td> <td>10</td> </tr> <tr> <th>5</th> <td>4</td> <td>0</td> <td>0</td> <td>16</td> <td>3</td> <td>2026</td> <td>12</td> <td>1</td> <td>4</td> <td>3</td> </tr> <tr> <th>6</th> <td>7</td> <td>5</td> <td>3</td> <td>0</td> <td>5</td> <td>2</td> <td>2245</td> <td>0</td> <td>4</td> <td>0</td> </tr> <tr> <th>7</th> <td>1</td> <td>6</td> <td>11</td> <td>2</td> <td>5</td> <td>1</td> <td>0</td> <td>2373</td> <td>5</td> <td>13</td> </tr> <tr> <th>8</th> <td>3</td> <td>9</td> <td>4</td> <td>9</td> <td>4</td> <td>10</td> <td>2</td> <td>3</td> <td>2166</td> <td>5</td> </tr> <tr> <th>9</th> <td>3</td> <td>2</td> <td>2</td> <td>6</td> <td>19</td> <td>6</td> <td>0</td> <td>12</td> <td>10</td> <td>2329</td> </tr> </tbody> </table> <ul> <li>Accuracy: 98.40%</li> <li>Error: 1.60%</li> </ul> <p>Looks pretty good to me. However, note that there are much better results. The best on <a href="http://yann.lecun.com/exdb/mnist/">the official website</a> has an error of 0.23% and is a committee of 35 convolutional neural networks.</p> <p>The best SVM I could find has an error of 0.56% and applies a polynomial kernel of degree 9 as well as some preprocessing.</p> <h2 id="references">References</h2> <ul> <li>[<a href="#ref-smi04-anchor" name="ref-smi04">Smi04</a>] B. T. Smith, “Lagrange multipliers tutorial in the context of support vector machines,” Memorial University of Newfoundland St. John’s, Newfoundland, Canada, Jun. 2004.</li> <li>[<a href="#ref-bur98-anchor" name="ref-bur98">Bur98</a>] C. J. Burges, “<a href="http://research.microsoft.com/pubs/67119/svmtutorial.pdf">A tutorial on support vector machines for pattern recognition</a>”, Data mining and knowledge discovery, vol. 2, no. 2, pp. 121–167, 1998.</li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="http://scikit-learn.org/stable/auto_examples/classification/plot_digits_classification.html">Recognizing hand-written digits</a></li> <li>Trung Huynh’s tech blog: <a href="http://www.trungh.com/2013/04/digit-recognition-using-svm-in-python/">Digit Recognition using SVM in Python</a></li> <li><a href="http://scikit-learn.org/stable/auto_examples/classification/plot_classifier_comparison.html">Classifier comparison</a></li> <li><a href="http://scikit-learn.org/stable/supervised_learning.html">Supervised learning</a></li> </ul> Explaining Away //martin-thoma.com/explaining-away/ Mon, 04 Jan 2016 23:52:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/explaining-away <p>Explaining away is an effect where which is explained in Pearl (1988) with an example similar to the following one:</p> <blockquote> <p>A car’s engine can fail (\(X\)). The reason might either be a dead battery \(Y\) or a blocked fuel pump \(Z\).</p> </blockquote> <p>This results in the following Bayesian Network:</p> <div style="width: 109px" class="wp-caption aligncenter"><a href="../images/2016/01/Common-effect.png"><img src="../images/2016/01/Common-effect.png" alt="A common effect" width="" height="" class="" /></a><p class="wp-caption-text">A common effect</p></div> <p>Now assume you know that the engine does not fail (\(X=0\)). This guarantees that the battery is not dead (\(Y=0\)) and the fuel pump is not blocked (\(Z=0\)).</p> <p>However, if the engine failed (\(X=1\)) it gets more interesting. Let’s say the engine works with a probability of 90%. From the graph, you can see that we assume that a dead battery is independant of a blocked fuel pump. Let’s also assume that you know that either the fuel pump is blocked or the battery is dead when the engine failed. There is no other option.</p> <p>This makes setting the probability distribution up interesting. There is still 10% left which has to be distributed amongst \(P(X=1,Y=1,Z=1), P(X=1,Y=1,Z=0), P(X=1,Y=0,Z=1)\):</p> <table> <thead> <tr> <th>X</th> <th>Y</th> <th>Z</th> <th>P(X,Y,Z)</th> <th>comment</th> </tr> </thead> <tbody> <tr> <td>0</td> <td>0</td> <td>0</td> <td>0.9</td> <td>Engine works</td> </tr> <tr> <td>0</td> <td>0</td> <td>1</td> <td>0</td> <td>impossible - blocked fuel pump and working engine</td> </tr> <tr> <td>0</td> <td>1</td> <td>0</td> <td>0</td> <td>impossible - dead battery and working engine</td> </tr> <tr> <td>0</td> <td>1</td> <td>1</td> <td>0</td> <td>impossible - dead battery, blocked fuel pump and working engine</td> </tr> <tr> <td>1</td> <td>0</td> <td>0</td> <td>0</td> <td>impossible - a cause we don’t have in our graph</td> </tr> <tr> <td>1</td> <td>0</td> <td>1</td> <td>a</td> <td> </td> </tr> <tr> <td>1</td> <td>1</td> <td>0</td> <td>b</td> <td> </td> </tr> <tr> <td>1</td> <td>1</td> <td>1</td> <td>c</td> <td> </td> </tr> </tbody> </table> <p>However, if you assume that \(Y\) and \(Z\) are independent, given \(X\), then you would have to set \(P(Y=0, Z=0|X=1) = P(Y=0|X=1) \cdot P(Z=0|X=1)\) which would not be 0 except one of the probabilities would be 0. Or, putting it different again: Given that you know the engine is broken, the event of a dead battery and a blocked fuel pump are suddenly not independent anymore!</p> <h2 id="what-does-it-mean">What does it mean</h2> <p>This does not mean there is “suddenly” a causatal connection between a dead battery and a blocked fuel pump. It only means you can learn something for your predictions.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="http://stats.stackexchange.com/q/54849/25741">Why does “explaining away” make intuitive sense?</a></li> <li><a href="https://en.wikipedia.org/wiki/Interaction_information#Example_of_Positive_Interaction_Information">Interaction information</a></li> </ul> How to clear a USB stick //martin-thoma.com/clear-usb-stick/ Sat, 02 Jan 2016 22:57:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/clear-usb-stick <p>Once in a while I think it is time to reduce the damage being done by the loss of a USB stick.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2016/01/usb-sticks.jpg"><img src="//martin-thoma.com/captions/usb-sticks.jpg" alt="USB sticks" width="500" height="375" class="" /></a><p class="wp-caption-text">USB sticks</p></div> <h2 id="remove-all-data">Remove all data</h2> <p>Find the USB stick on your Linux system with <code>fdisk -l</code>. Make super sure that you really got the stick (e.g. by removing it and executing the command again). It should be something like <code>/dev/sdb1</code>.</p> <p>The following command will overwrite the data on the stick 5 times:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ shred -f -n 5 /dev/sdX </pre></div> </div> </div> <p>This may take several minutes even for very small USB sticks.</p> <h2 id="format-the-stick">Format the stick</h2> <p>Start <code>gparted</code> and use the GUI.</p> <p>See also: <a href="http://askubuntu.com/q/22381/10425">How to format a USB flash drive?</a></p> <h2 id="add-readme">Add README</h2> <p>In case I lose the stick, adding a README.txt makes with a way to contact me makes it most likely that I get the stick back.</p> <pre><code>Dieser USB-Stick ging verloren. Mein Name ist Martin Thoma. Sie können mich per E-Mail unter info@martin-thoma.de erreichen. --- This USB-Stick was lost. My name is Martin Thoma. You can contact me via e-mail: info@martin-thoma.de </code></pre> Preparing for the New Year //martin-thoma.com/new-year-2016/ Thu, 31 Dec 2015 14:37:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/new-year-2016 <p>It’s new years eve and - as always - I try to finish some things and have some plans for next year.</p> <h2 id="review-of-2015">Review of 2015</h2> <p>The last year has had it ups and downs. Most of them are private, so I’ll not write too much about it. However, I would like to share two of them with you: I’ve been on my first summer school of the German National Academic Foundation (Sommerakademie der Studienstiftung, see <a href="https://commons.wikimedia.org/wiki/Category:Images_by_Martin_Thoma/Sommerakademie-2015">photos</a>) and I’ve been for two weeks hiking the west highland way (see <a href="https://commons.wikimedia.org/wiki/Category:Images_by_Martin_Thoma/WHW">photos</a>). This month was really awesome.</p> <p>Here are some other mentionable facts:</p> <ul> <li>I’ve founded <strong>Machine Learning Karlsruhe</strong>. See <a href="http://ml-ka.de">ml-ka.de</a> for more information.</li> <li>I’ve got 10 000 points on StackOverflow and reached 2.5 million people with my questions and answers (<a href="http://stackoverflow.com/users/562769/moose">source</a>)</li> <li>I’ve got the funding by the <a href="http://www.begabtenstiftung-informatik.de/">Begabtenstiftung</a> to go with my friend Marvin to Berkeley. Let’s see if Berkeley accepts us.</li> <li>I’ve published 4 papers on arXiv (<a href="http://arxiv.org/a/thoma_m_1.html">link</a>) (one is still on hold) and started building an academic profile with <a href="http://orcid.org/0000-0002-6517-1690">orcid.org/0000-0002-6517-1690</a>. I’m not sure how important that will be, though.</li> <li>I posted 36 articles on my blog in 2015. However, I don’t think there is a single good article amongst them. I simply didn’t have enough time to write an interesting article ☹. There are 47 drafts from 2015; 134 drafts in total.</li> <li><a href="http://write-math.com/">write-math.com</a> now has <ul> <li>2520 users who contributed something</li> <li>1595 formulas (that includes simple symbols)</li> <li>274244 recordings. 6495 of those are not classified yet.</li> </ul> </li> </ul> <h2 id="finishing-things">Finishing Things</h2> <p>I always do some cleanup before the new year begins. This means especially cleaning my computer stuff of unnecessary trash.</p> <h3 id="e-mail">E-Mail</h3> <p>Finding and deleting old unnecessary emails:</p> <ul> <li>StackExchange: do-not-reply@stackexchange.com</li> <li>University <ul> <li>physik-l@lists.kit.edu</li> <li>physik-ll@lists.kit.edu</li> <li>stipendiaten@lists.does-not-exist.org</li> <li>ilias@scc-ilias-03.scc.kit.edu</li> </ul> </li> <li>Programming <ul> <li>notifications@travis-ci.org</li> <li>noreply@coursera.org</li> </ul> </li> <li>Other <ul> <li>notify@twitter.com</li> <li>jobs-listings@linkedin.com</li> <li>messages-noreply@linkedin.com</li> <li>noreply@indiegogo.com</li> <li>mailing@abgeordnetenwatch.de</li> <li>offener-haushalt-request@lists.okfn.org</li> <li>infoen@bondora.com</li> </ul> </li> </ul> <p>This were several hundret emails.</p> <p>The next step is going through “marked emails”.</p> <h3 id="desktop-and-downloads">Desktop and Downloads</h3> <p>Clean those folders up … *sigh*… I didn’t get ready.</p> <h3 id="updating">Updating</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># apt-get update # apt-get upgrade $ upgrade_oh_my_zsh </pre></div> </div> </div> <h2 id="plans">Plans</h2> <p>I want to get the following things done in 2016:</p> <ul> <li>[ ] Quit church: That one is actually more complicated in Germany than it should be. I have to get to the civil registry office, get a <strong>personal</strong> date, <strong>pay 31.50 Euro</strong> (Source: <a href="https://web1.karlsruhe.de/service/d115/detail.php?prod_id=463">karlsruhe.de</a>)</li> <li>[ ] Migrate from <a href="https://jekyllrb.com/">Jekyll</a> to <a href="http://docs.getpelican.com/">Pelican</a> (see <a href="https://github.com/MartinThoma/MartinThoma.github.io/blob/source/_drafts/2015-11-13-migrate-from-jekyll-to-pelican.md">article draft</a>)</li> <li>[ ] Get all my stuff from my fathers apartment to my room. I’ve already packed most of it in boxes (In total: 1.30m (+0.30m?) × 0.39m × 0.60m by 7 boxes)</li> <li>[ ] Get rid of my old bed</li> <li>[ ] Get rid of my old vacuum cleaner</li> <li>[ ] Paint the wall</li> <li>[ ] Contact BSI, BKA, CCC and the car sellers and send them my paper in which I summarize current problems in car security.</li> <li>[ ] Getting new slippers</li> </ul> <p>Of course, I have a lot of other plans. Although some people say I don’t do anything besides computer stuff, I do have a prive life. But in contrast to others I like to keep it private.</p> <p>I wish all of you a happy new year!</p> <h2 id="predictions-for-2016">Predictions for 2016</h2> <p>I’ve just seen <a href="http://blog.computationalcomplexity.org/2016/01/predictions-of-new-year.html">Predictions for 2016</a> on Computational Complexity and thought it is a fun idea. It is currently the 4th of January, so the year is still young enough to not consider this cheating:</p> <p>Machine Learning and Technology</p> <ol> <li>Networks will get deeper. Currently about 8 layers is usual; I expect this to get to over 30 layers.</li> <li>First hacks / funny results by people abusing the fact that machine learning is used will appear.</li> <li>Machines will generate “high” resolution images of at least 256 &amp;times 256 pixels.</li> <li>Speech synthesis will fastly improve. To benchmark this, I will use the original quotation that explained the importance of towels is found in Chapter 3 of Adams’ work The Hitchhiker’s Guide to the Galaxy. See <a href="https://en.wikipedia.org/wiki/Towel_Day">Towel Day</a>, <a href="//martin-thoma.com/audio/2016-01-04-towel-quote-google.ogg">Google Translate Recording</a>, <a href="//martin-thoma.com/audio/2016-01-04-towel-quote-festival.ogg">Festival Recording</a></li> <li>ALPHABET INC. (C) (GOOGLE) shares at Frankfurt Stock Exchange will go up to about 900 Euro sometime in the year (currently, it is at 690 Euro).</li> <li><a href="http://www.solarroadways.com/">Solar Roadways</a> will make some tiny advances.</li> </ol> <p>About Me</p> <ol> <li>One of my papers will get cited at least 5 times.</li> <li>I will spend at least 2 weeks abroad.</li> <li>I will publish at leat 40 articles on my blog.</li> <li>I will get a 90 days streak on GitHub (currently, my longest is 43 days).</li> <li>I will get 15 000 points on StackExchange (see <a href="http://stackexchange.com/users/271958/moose?tab=accounts">StackExchange profile</a>)</li> </ol> <p>Politics</p> <ol> <li>The <a href="https://en.wikipedia.org/wiki/European_Union">European Union</a> will still exist and Britain will still be part of it (see <a href="https://de.wikipedia.org/wiki/Brexit">Brexit</a>).</li> <li>Donald Trump will be the republican candidate and Hillary Clinton the democrat candidate.</li> <li>The republican candidate will get president.</li> <li>More mass shootings in the US and terrorist attacks all over the world will happen.</li> <li>Grüne and SPD will still be in Baden-Württemberg (see <a href="https://de.wikipedia.org/wiki/Landtagswahl_in_Baden-W%C3%BCrttemberg_2016">Landtagswahl in Baden-Württemberg 2016</a>).</li> </ol> Analyzing PyPI Data - 2 //martin-thoma.com/analyzing-pypi-metadata-2/ Wed, 30 Dec 2015 13:28:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/analyzing-pypi-metadata-2 <div class="info">This is part two of a series. See <a href="//martin-thoma.com/analyzing-pypi-metadata/">Analyzing PyPI Data</a> for part one.</div> <p>I’ve recently got a request to expand my analysis of the Python Package Index commonly known as PyPI. It is a repository of Python packages where everybody can upload packages; pretty much without any restriction. In the article <a href="//martin-thoma.com/analyzing-pypi-metadata/">Analyzing PyPI Metadata</a> you can read some general stuff about the repository.</p> <p>This article is going a bit more deeper. This time I don’t only analyze the metadata, but the relationship of the packages themselves. I wanted to build a dependency graph. However, here is a downside of Pythons package structure: The file which defines the dependencies of a Python package is a Python script itself. This gives the package developer the highest flexibility, but it also gives them the power to execute arbitrary code when I only want to get the dependencies.</p> <p>As I am pretty sure there are some malicious packages in the repository (Although I’ve never heard of a single one there has to be one. Over 50 000 packages by 2015 - there has to be one!). So I don’t want to execute any code of the repository without having at least a clue what it should do. This means my analysis is very simple and thus prone to some errors.</p> <h2 id="most-common-single-dependency">Most common single dependency</h2> <p>One can see dependencies as being weighted by the number of times a package imports the package.</p> <h3 id="non-weighted">Non-weighted</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">20</span> </pre></div> </div> </div> <p>which gives</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/pypi-imported-packages-count.png"><img src="//martin-thoma.com/captions/pypi-imported-packages-count.png" alt="This bar chart displays which Python modules get imported by most Python packages" width="500" height="230" class="" /></a><p class="wp-caption-text">This bar chart displays which Python modules get imported by most Python packages</p></div> <p>and without the system packages:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">on_pypi</span><span style="color:#710">`</span></span> = <span style="color:#00D">1</span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">20</span> </pre></div> </div> </div> <p>which gives</p> <figure style="width: 510px" class="wp-caption aligncenter"> <img src="../images/2015/12/pypi-imported-packages-excluding-system-count.png" alt="This bar chart displays which Python modules (excluding system modules) get imported by most Python packages" /> <figcaption>This bar chart displays which Python modules (excluding system modules) get imported by most Python packages</figcaption> </figure> <h3 id="weighted">Weighted</h3> <p>How often gets a single module included over all packages?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">SUM</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">times</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">SUM</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">times</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">20</span> </pre></div> </div> </div> <p>2 seconds later I’ve got the result:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/pypi-imported-packages.png"><img src="//martin-thoma.com/captions/pypi-imported-packages.png" alt="Number of imports of Python packages" width="500" height="215" class="" /></a><p class="wp-caption-text">Number of imports of Python packages</p></div> <p>If I’m only interested in the packages which are on PyPI, hence not system packages, I execute the following query:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">SUM</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">times</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">on_pypi</span><span style="color:#710">`</span></span> = <span style="color:#00D">1</span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">SUM</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">times</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">20</span> </pre></div> </div> </div> <p>which gives me about 2 seconds later the following result:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/pypi-imported-packages-excluding-system.png"><img src="//martin-thoma.com/captions/pypi-imported-packages-excluding-system.png" alt="Number of imports of Python packages, excluding system packages" width="500" height="216" class="" /></a><p class="wp-caption-text">Number of imports of Python packages, excluding system packages</p></div> <h2 id="non-functional-packages">Non-functional packages</h2> <p>Although there are many packages for Python which are very useful, there are also quite a lot which are not usefull at all. One possibility to identify such packages is by checking which packages get neither used by others nor use other packages</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">in</span> ( <span style="color:#B06;font-weight:bold">SELECT</span> <span style="color:#080;font-weight:bold">DISTINCT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">package</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> dependencies) <span style="color:#080;font-weight:bold">OR</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">in</span> ( <span style="color:#B06;font-weight:bold">SELECT</span> <span style="color:#080;font-weight:bold">DISTINCT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">needs_package</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">dependencies</span><span style="color:#710">`</span></span>) </pre></div> </div> </div> <p>This leads to the result that 54 900 packages of 67 582 packages are not obviously crap. Or to write it in another way: 11 682 packages are crap. That is 17.5 %. Too much, in my opinion. However, this might also be due to my crappy script not downloading / checking the downloaded files correctly.</p> <h2 id="names">Names</h2> <p>One thing I was interested in while downloading all those packages was the question if there are malicious packages (either on purpose or by accident). One undesirable thing that could happen would be very similar names.</p> <h3 id="prefixes">Prefixes</h3> <p>Let’s see how many packages are prefixes of other packages. My thought was that this might be developers trying to get some accidential installs. However, it only showed some relationships. I wanted to make a Levensthein distance analysis, but I guess this is not worth it.</p> <p>Here are the top 10 strings which are prefixes of packages and packages themselves:</p> <ol> <li>djan: 6462</li> <li>pyt: 1626</li> <li>pyth: 1278</li> <li>collect: 1155</li> <li>Flask: 561</li> <li>open: 474</li> <li>pyr: 442</li> <li>pyp: 295</li> <li>pyra: 285</li> <li>pym: 256</li> </ol> <p>One interesting thing I’ve learned is that you can use <code>pip</code> like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pip search &quot;djan$&quot; </pre></div> </div> </div> <p>… and I found a pip bug (<a href="https://github.com/pypa/pip/issues/3327">github.com/pypa/pip/issues/3327</a>)</p> <h2 id="graph-analysis">Graph analysis</h2> <p>Analyzing the dependency graph is quite a challenge. Or at least that was what I initiallly thought. This graph has about 67 582 nodes and 436 980 edges. Quite a bit. Definitely much larger than what I have previously used.</p> <p>However, my friend Nilan who knows a lot about graphs send me a link to StackOverflow: <a href="http://stackoverflow.com/q/238724/562769">Visualizing Undirected Graph That’s Too Large for GraphViz?</a></p> <p>This lead me to <a href="http://gephi.org/">Gephi</a> and the <a href="https://marketplace.gephi.org/plugin/openord-layout/">OpenOrd</a> layout plugin. It didn’t work for the complete graph (see <a href="https://github.com/gephi/gephi/issues/1207">issues/1207</a>), it worked after I removed the single nodes without edges.</p> <p>Now we can ask several standard questions about graphs:</p> <ul> <li>How many connected components are there?</li> <li>Are there any circles? (That would be bad… dependency graphs should not have circles. Similar to family trees.)</li> <li>Which are the most central nodes?</li> </ul> <p>I didn’t find the time to answer those, but I put the graph data in JSON format on <a href="https://github.com/MartinThoma/pypi-dependencies">github.com/MartinThoma/pypi-dependencies</a>. Please let me know when you do something interesting with the data.</p> <p>I’ve only got some crappy images with Gephi / GraphViz:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 489px; width: 489px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/pypi-rendered.png" class="image"><img src="//martin-thoma.com/captions/pypi-rendered.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/pypi-rendered-circo-5000-x-small.png" class="image"><img src="//martin-thoma.com/captions/pypi-rendered-circo-5000-x-small.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/pypi-rendered-twopi.png" class="image"><img src="//martin-thoma.com/captions/pypi-rendered-twopi.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/pypi-rendered-x.png" class="image"><img src="//martin-thoma.com/captions/pypi-rendered-x.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/gephi-1.png" class="image"><img src="//martin-thoma.com/captions/gephi-1.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/gephi-2.png" class="image"><img src="//martin-thoma.com/captions/gephi-2.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/12/pypi-graph-small.png" class="image"><img src="//martin-thoma.com/captions/pypi-graph-small.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <h2 id="code">Code</h2> <p>See <a href="https://github.com/MartinThoma/algorithms/tree/master/PyPI">github.com/MartinThoma/algorithms</a>.</p> <h2 id="what-could-come-next">What could come next</h2> <p>I would like too measure the overall code quality on PyPI in another post. I think of the following measures:</p> <ul> <li><a href="https://pypi.python.org/pypi/pyroma">pyroma</a>: A 10-point score for packages</li> <li>package goodness with <a href="https://pypi.python.org/pypi/Cheesecake">Cheesecake</a>,</li> <li><a href="https://pypi.python.org/pypi/pylint">pylint</a></li> <li>PEP8 conformance,</li> <li>Lines of code (LOC) / documentation / whitespace</li> <li>Docstring style (None, NumpyDoc, Sphinx, Google - see <a href="http://martin-thoma.com/python-code-documentation/">Python Code Documentation</a>)</li> <li>Usage of functions</li> <li>Testing coverage</li> <li>Look for URLs in the code and which are reachable / which are not</li> <li>Look for non-Python files</li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="https://gephi.org/tutorials/gephi-tutorial-quick_start.pdf">Quick Start with Gephi</a></li> <li><a href="http://gephi.org/features/">Features of Gephi</a></li> </ul> How to find new Papers //martin-thoma.com/find-papers/ Thu, 03 Dec 2015 07:30:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/find-papers <p>A couple of people who are just participating in their first seminar might ask themselves how you can find interesting new publications (papers). I would like to shed some light on it.</p> <h2 id="initial-research">Initial Research</h2> <p>The hardest part is when you’re new to a field. You don’t know which journals are the important ones, which authors are most respected in the field, which terms are used.</p> <h3 id="journal-rankings">Journal Rankings</h3> <p>Automated journal rankings like the h5-index used by Google Scholar (see <a href="https://scholar.google.com/intl/en/scholar/metrics.html">metrics</a>, <a href="https://en.wikipedia.org/wiki/H-index">Wikipedia</a>) is one way to deal with the lack of domain knowledge. Google Scholar even publishes a list of journals per field (see <a href="https://scholar.google.com/citations?view_op=top_venues&amp;hl=en&amp;vq=eng_computervisionpatternrecognition">Top publications in Computer Vision and Pattern Recognition</a>).</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/google-scholar-top-publications.png"><img src="//martin-thoma.com/captions/google-scholar-top-publications.png" alt="Google Scholar Journal ranking" width="500" height="237" class="" /></a><p class="wp-caption-text">Google Scholar Journal ranking</p></div> <h3 id="algorithmic-ideas">Algorithmic Ideas</h3> <p>I’ve never tried it (on purpose), but the idea just came to my head: Use a random walk. You start with some paper of which you don’t really know if it is good. Look at the references and try to weild out the ones which are obviously not work trying (e.g. because they are websites). Now take a random one to continue with. Do this a couple of times.</p> <p>The idea is that papers which are more important are much more often cited. So you can hope to get to more important papers over time.</p> <h3 id="the-hard-way">The hard way</h3> <p>Search for papers via Google. Look at the references. Search for papers in the reference. Get a feeling for the language being used.</p> <h2 id="ongoing-research">Ongoing Research</h2> <p>When you have a little bit of domain knowledge (or a starting paper given to you by your supervisor) everything gets a lot easier.</p> <p>There are a couple of key strategies:</p> <ul> <li>Looking at the references of a paper</li> <li>Looking at what else the same author published</li> <li>Looking for similar titles</li> <li>Reading Journals</li> </ul> <p>For all three of them, I can highly recommend <a href="https://scholar.google.com">Google Scholar</a>. They also offer a nice overview / statistics about authors so that you can get a feeling for their scientific activity. But don’t let you fool you by those numbers: It is possible to fake them.</p> <p>The other nice thing is that Google Scholar makes citing publications incredibly easy:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/google-scholar-paper.png"><img src="//martin-thoma.com/captions/google-scholar-paper.png" alt="Searching for a publication on Google Scholar" width="500" height="234" class="" /></a><p class="wp-caption-text">Searching for a publication on Google Scholar</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/citation.png"><img src="//martin-thoma.com/captions/citation.png" alt="Citing a publication via Google Scholar" width="500" height="341" class="" /></a><p class="wp-caption-text">Citing a publication via Google Scholar</p></div> <h3 id="the-arxiv">The arXiv</h3> <p>The arXiv can be seen as THE “modern way” journal. Depending on the field, it has a VERY high reputation.</p> <p>For Pattern Recognition the reputation of the arXiv is amongst the highest ten journals, but it there are some fields like physics where it is THE top journal in several subfields like cosmology or high energy physics.</p> <p>What makes the arXiv stand out is the fact that you can read new papers every day. I like to have a view at <a href="http://arxiv.org/list/cs.CV/recent">cs.CV/recent</a> to keep myself informed about new stuff. There are about 20 new publications per day. On some days, there is nothing interesting, on other days like today quite a bit:</p> <ul> <li><a href="http://arxiv.org/pdf/1512.00596.pdf">The MegaFace Benchmark: 1 Million Faces for Recognition at Scale</a></li> <li><a href="http://arxiv.org/pdf/1512.00567.pdf">Rethinking the Inception Architecture for Computer Vision</a></li> <li><a href="http://arxiv.org/pdf/1512.00517.pdf">Labeling the Features Not the Samples: Efficient Video Classification with Minimal Supervision</a></li> <li><a href="http://arxiv.org/pdf/1512.00570.pdf">Attribute2Image: Conditional Image Generation from Visual Attributes</a></li> </ul> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/latest-arxiv-publications.png"><img src="//martin-thoma.com/captions/latest-arxiv-publications.png" alt="Latest submissions on arXiv in Pattern Recognition and Computer Vision" width="500" height="328" class="" /></a><p class="wp-caption-text">Latest submissions on arXiv in Pattern Recognition and Computer Vision</p></div> <h2 id="filtering">Filtering</h2> <p>I filter publications like this:</p> <ul> <li>First, I look at the title. If that doesn’t look interesting, I skip it. The more exact the title is, the better. If it is too vague, I sometimes skip it too because the authors seem not to be familiar with the scientific style of writing and thus are probably not able to write an interesting paper.</li> <li>Then I read the abstract. I expect to get to know what the paper is about.</li> <li>Then I look at images / tables (depending on the subject)</li> <li>I read the conclusion / last part</li> <li>I read the end of the introduction where it often says “the paper is structured as follows”</li> </ul> <p>I guess many researchers filter like this. This is important to know when you write a paper.</p> OpenBCI //martin-thoma.com/openbci/ Thu, 26 Nov 2015 22:40:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/openbci <p>I’ve just discovered the <a href="https://www.kickstarter.com/projects/openbci/openbci-biosensing-for-everybody">OpenBCI: Biosensing for Everybody</a> Kickstarter project. BCI is short for Brain Computer Interface. This Kickstarter is about an <abbr title="Electroencephalography">EEG</abbr> device. Such a device looks like a helmet. It has several electrodes which you place on your scalp. Those electrodes measure “voltage fluctuations resulting from ionic current within the neurons of the brain” (source: <a href="https://en.wikipedia.org/wiki/Electroencephalography">Wikpedia</a>).</p> <p>I’m really curious about this, because I recently had some thoughts that medicine is currently not working as I want it to be. Doctors rely on the information they get by their patients, and they shouldn’t. Patients can either directly lie or say something which is not try by accident. Instead of taking this feedback from patients, decisions should more often rely on hard data.</p> <p>For locked-in people, that means people who have sever difficulties to communicate with the outside world, it would be awesome if we could use BCIs to help them. I know this is far in the future, but you have to start at some point.</p> <p>Another use I would really be curious is some kind of “automatic interrogation”. Think of terrorists / criminals who got caught, but are not willing to give the police necessary information. I think we should have the possibility to extract this kind of information from them, without hurting them. This idea was mentioned in one of the books of <a href="https://en.wikipedia.org/wiki/Daniel_Suarez_(author)">Daniel Suarez</a>; I think it was <a href="https://en.wikipedia.org/wiki/Daemon_(novel_series)">Daemon</a>.</p> <p>The last nice application of BCIs would be REALLY convenient ways to interact with computers. Again, this is something really far in the future, but an awesome idea ☺</p> <h2 id="the-perks">The Perks</h2> <h3 id="ganglion">Ganglion</h3> <p>It is an EEG board. Whatever that means:</p> <blockquote> <p>The OpenBCI Ganglion is a high-quality, affordable bio-sensing device. On the input side, there are 4 high-impedance differential inputs, a driven ground (DRL), a positive voltage supply (Vdd), and a negative voltage supply (Vss). The inputs can be used as individual differential inputs for measuring EMG or ECG, or they can be individually connected to a reference electrode for measuring EEG.</p> </blockquote> <h3 id="ultracortex-mark-iv">Ultracortex Mark IV</h3> <p>The Ultracortex Mark IV is an EEG headset.</p> <blockquote> <p>The Ultracortex Mark III is the latest working version of the OpenBCI headset. You can find all of the 3D files. links to hardware, and an assembly on our Github repo. We designed it for maximum adjustability and ease of use. In our design thinking, we prioritized the use of dry electrodes (pictured in the images above). Using dry sensors significantly reduces the time needed for setup (no more sticky paste!) and makes the overall experience of wearing the headset much more pleasant.</p> </blockquote> <p>There are three options:</p> <blockquote> <ul> <li>Print-It-Yourself (`$350): this reward comes with all of the pieces required to assemble a full Ultracortex Mark IV aside from the pieces you can print yourself with a desktop 3D-printer, in addition to an OpenBCI Ganglion Board. This kit is perfect for backers who have their own 3D-printer.</li> <li>Unassembled ($`450): this reward comes with all of the pieces required to assemble a full Ultracortex Mark IV headset, including the pieces that are 3D-printable, and an OpenBCI Ganglion Board.</li> <li>Fully Assembled ($650): if you select this reward, you will receive a fully- assembled Ultracortex Mark IV with an OpenBCI Ganglion Board. It will arrive ready to plug in and fire up!</li> </ul> </blockquote> <p>What I would expect from it to be able to differentiate at least five different kinds of signals which I can willently make. Why five?</p> <ul> <li>Up</li> <li>Down</li> <li>Right (Yes)</li> <li>Left (No)</li> <li>Enter</li> </ul> <p>With those, you can make a virtual keyboard which is usable. Of course, you can also do so with two actions (next, enter), but that is MUCH more of a pain. The more different signals you can distinguish, the better.</p> <p>I also expect it to be able to see when I feel pain or when I sleep.</p> <h4 id="specs">Specs</h4> <p>Currently, there are basically no specs available (see <a href="https://www.kickstarter.com/projects/openbci/openbci-biosensing-for-everybody/comments">comments</a>). Some comments seem to suggest that there are only 16 electrodes in use. Then they speak about a 10-20 and a 10-10 system. I have no idea what that means.</p> <h2 id="the-people-behind-it">The People behind it</h2> <p>The project is done by <a href="https://www.linkedin.com/in/joel-murphy-a402733">Joel Murphy</a> and <a href="https://www.linkedin.com/in/conor-russomanno-90077425">Conor Russomanno</a>. They seem to have made a similar Kickstarter called “Spiderclaw”, but I could only find the <a href="https://github.com/OpenBCI/Spiderclaw">GitHub repository</a>. They also said they are affiliated with <a href="https://www.kickstarter.com/projects/1342192419/pulse-sensor-an-open-source-heart-rate-sensor-that">Pulse Sensor</a></p> <p>In a video, Paul Sajda (PhD, Professor of Biomedical Engineering and Radiology at Columbia University, <a href="http://bme.columbia.edu/paul-sajda">source</a>) says it is a “high quality recording system”.</p> <p>Ashley E. Stewart (CSO of <a href="http://www.neuromore.com/team/">Neuromore</a>, see also <a href="http://www.brainbodyperformance.com/aboutdrashleyestewart/dr-ashley-e-stewart/">brainbodyperformance.com</a>)</p> <p>Aaron Trocola (Industrial Designer at <a href="http://threeformfashion.com/">Threeform</a>) seems to be the person who designs the 3D printed parts.</p> <p>David Putrino, Department of Rehabilitation Medicine <a href="https://en.wikipedia.org/wiki/Weill_Cornell_Medicine">Weill Cornell Medical College</a> (<a href="http://www.burke.org/research/faculty/31">source</a>) also said a couple of positive words about it.</p> <h2 id="conclusion">Conclusion</h2> <p>By now, this project does not give me the impression that it is ready-to-use. I am still waiting for some feedback, but I guess I will rather wait for other (independant) people writing reviews about it. Preverably mentioning it in scientific papers which get published in notable journals or cited by enough other people.</p> <h2 id="articles">Articles</h2> <p>I couldn’t find any articles about OpenBCI on <a href="https://scholar.google.de/">scholar.google.com</a>, except for the following:</p> <p><a href="https://github.com/chipaudette">Chip Audette</a>, “Mind Control”, IEEE Spectrum. October 2015. DOI <a href="http://ieeexplore.ieee.org/xpl/articleDetails.jsp?arnumber=7274184">10.1109/MSPEC.2015.7274184</a>. Also: <a href="http://eeghacker.blogspot.de/">eeghacker.blogspot.de</a></p> <h2 id="links">Links</h2> <ul> <li>32c3: <a href="https://www.youtube.com/watch?v=en-TDIdeA_g">Evolution of Brain-Computer Interfaces</a> on YouTube. 28 December 2015.</li> <li><a href="http://openbci.com/">openbci.com</a></li> <li><a href="http://braintech.pl/openbci-pl/">openbci.pl</a> seems to be something different? But it has a publication <a href="http://dx.doi.org/10.2478/v10175-012-0054-1">User-centered design of brain-computer interfaces: OpenBCI.pl and BCI Appliance</a></li> <li><a href="https://github.com/OpenBCI/Ultracortex">github.com/OpenBCI/Ultracortex</a>: Instructions how to assemble the Utracortex Mark 1 - Mark 3</li> </ul> Terror in Paris //martin-thoma.com/terror-in-paris/ Sun, 15 Nov 2015 10:29:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/terror-in-paris <p>Recently, a huge terrorist attack happened in France (see <a href="https://en.wikipedia.org/wiki/November_2015_Paris_attacks">Wikipedia</a>). At least 129 people died and 352 people were injured. The attack happened on the evening of 13 November 2015. 6 mass shootings and 3 suicide bombings happened.</p> <p>What happened and the reactions I’ve seen so far make this the European / French equivalent of <a href="https://en.wikipedia.org/wiki/September_11_attacks">September 11 attacks</a>. A lot of people died or were injured, one of the most important cities were affected, politicians say we are in war, on Facebook people show condolence.</p> <h2 id="questions-we-need-to-ask">Questions we need to ask</h2> <ul> <li><strong>The Terrorists</strong>: Who were the terrorists? What was their story? How did they become terrorists?</li> <li><strong>The Weapons</strong>: Where did they get the weapons from? Can we prevent that?</li> <li><strong>Fast reactions</strong>: How could the police react that fast?</li> <li><strong>Future</strong>: How do we want to deal with such attacks?</li> </ul> <h3 id="the-terrorists">The Terrorists</h3> <p><a href="https://en.wikipedia.org/wiki/Islamic_State_of_Iraq_and_the_Levant">ISIS</a> claims they were responsible for the attacks. We could stop to think here and many certainly will. It is a terrorist organization and that is what terrorists do. The people were religiously motivated lunatics, so we don’t need to understand them. Right?</p> <p>Wrong.</p> <p>People are complicated. They don’t always act consistently. Their environment is critical to form who they are. If you grew up in an environment where you didn’t have reliable access to clean water, food, medical services, education, work, and a perspective on a good live in general, you would certainly be somebody else.</p> <p>Don’t get me wrong here. I don’t want to talk it little. Everybody has a choice what he can do in his live. What terrorists do is cruel. But just like after September 11, I am pretty sure we (France, Germany, Europe) will spend a lot of time and money in reaction to the attacks. One reaction we will certainly get is demands for more spendings / actions in military and surveillance. Demands for closing borders. What I want to say is that we are trying to intervene in a too late step of the “terror process”. People are not born terrorists. They become terrorists during their lives. We should not prevent terrorists from entering our countries, from blowing up what is important for us. We should prevent people from becoming terrorists.</p> <p>Now you might say that is easier said than done. But a very first step would be getting a detailed view of the terrorists lives. I don’t mean the preparation, but their complete live. Their environment. And then change that.</p> <p>My assumption is that we could completely prevent generations of terrorists from being born when we “simply” make the world better.</p> <h3 id="weapons">Weapons</h3> <p>According to the Paris prosecutor, the attackers wearing suicide vests used <a href="https://en.wikipedia.org/wiki/Acetone_peroxide">TATP</a> as an explosive. This is easy to make from things of everyday live. So we can’t prevent it from being made and used by suicide bombers, except if we massively sacrifice privacy. I’m talking here about cameras in your bedroom kind of surveillance. “Only” the US way of surveillance will not change anything.</p> <p>However, I’ve also read that the terrorists used <a href="https://en.wikipedia.org/wiki/AK-47">AK-47 rifles</a>. They cannot be build by yourself, so we should find out where they came from. One only the concrete path, but in general.</p> <h3 id="fast-reactions">Fast Reactions</h3> <p>It is less than two days after the attacks, and we already know which type of explosive the bombing vests were made of, some people were put into arrest, and we are sure that ISIS is responsible. This is astonishing. It feels as if the police was doing an extraordinary good job here. I wonder if it would be that fast outside of Paris.</p> <p>At the same time, it feels too fast. When we get news that fast, we (unconciously) will expect such fast reactions with other attacks. This might not be possible and people might - too fast - ask for political changes. I just want to point out that such fast reactions and the quick, not very well investigated articles we get today (like this one… but I’m not a journalist) are not always good for us.</p> <h2 id="possible-actions">Possible actions</h2> <p>I see three ways we, as a society, can react to terrorist attacks in general:</p> <ul> <li><strong>No reaction</strong></li> <li><strong>Surveillance and military</strong></li> <li><strong>Development aid</strong></li> </ul> <h3 id="no-reaction">No reaction</h3> <p>I was positively surprised how the people from Norway reacted to the <a href="https://en.wikipedia.org/wiki/2011_Norway_attacks">2011 Norway attacks</a>. They didn’t start new surveillance programs. They didn’t increase their military spendings.</p> <p>The Norwegians showed they are strong. They showed the world that they are united. They showed that they will not let terrorist attacks change the way they live their lives.</p> <h3 id="surveillance-and-military">Surveillance and military</h3> <p>When something happens, people want politicians to show they improve the situation. They want revenge. They want others to share their pain. They feel insecure and want to feel strong and secure again.</p> <p>This is a reason why spending more money in surveillance and military is a very understandable, logical reaction.</p> <p>But be clear what you’re doing when you ask for more spendings in military and surveillance. Be clear what you sacrifice when you want to expand the power of intelligence services. Think about how you let terrorists change your live. Which other dangers you might put your society into.</p> <p>I am a strong opponent of surveillance and also (not that much, but still) an opponent of military. One reason is that we are playing a stupid game (see <a href="https://www.schneier.com/essays/archives/2010/11/a_waste_of_money_and.html">A Waste of Money and Time</a>, a security expert). We see what terrorists did, like an attack with airplanes, and we as a society spend lots and lots of effort to prevent that. We accept being treated like criminals, hundred thousands of passengers, just to get a slight chance to catch a terrorist. The terrorists know that, so they can take the train and do exactly the same. We pick our defenses and they do something different.</p> <p>I don’t want to play such a stupid game.</p> <p>One way around is intelligence. But the bad thing is, that it doesn’t make sense to use a little bit of intelligence. You have to go the full, Orwellian way to have a good chance of it being effective. Here is what I could think of:</p> <ul> <li>Make money flows transparent: Don’t use cash any more. Only digital money which gets tracked by government agencies. Track who buys what in which quantities. Make shops, no matter how small, connect the transactions with goods you bought. This has to include everything, as you can use quite a lot of different things to build bombs.</li> <li>Track everybody: With smartphones you can make detailed movement profiles. Even if you’re not on Facebook, you can build a social graph. Who talked to whom, who has how much contact to whom. Who is influential, who isn’t.</li> <li>Get rid of privacy: We have surveillance equipment everywhere. Private smartphones, tablets, laptops usually have cameras and microphones. Most people use these devices to communicate. These devices, combined with traffic cameras, private shop / bank cameras give pretty detailed images of what is going on. An automatic computer system like Microsoft’s <a href="https://en.wikipedia.org/wiki/Domain_Awareness_System">Domain Awareness System</a> could constantly take this information and react within seconds.</li> </ul> <p>But we have to be aware of what we sacrifice when we are doing it. The surveillance systems can be hacked. They can be misused. The automatic algorithms can - just like humans - make mistakes.</p> <p>Imagine the world we would live in if the <a href="https://en.wikipedia.org/wiki/Gestapo">Gestapo</a> or the <a href="https://en.wikipedia.org/wiki/Stasi">Stasi</a> had access to this kind of technology. Imagine how people would act differently when they know everything they did was recorded and could be hold against them later.</p> <p>On the positive side: This could decrease “normal” crime, too.</p> <h3 id="development-aid">Development aid</h3> <p>Just as I began to write before, I would prefer if we spend more money on development aid. I am pretty sure there are many (potential) terrorists, which would not even consider that if they were in a better situation. We could massively improve the situation of the live of millions of people. Even if it would not work against terrorism, we would still do something inherently good. We would help the people. If we honestly want to improve their situation, if we don’t use military but humanitarian aid, people will recognize this. People will have something good in their minds when they thought of us (see <a href="http://www.spiegel.de/politik/deutschland/friedensdemo-brot-statt-bomben-a-160073.html">“Brot statt Bomben”</a>). A positive side-effect would be that it would stop coming more refugees to Europe.</p> <p>Of course, just throwing money at the problem will not solve anything. We need to check if the money actually gets to the people. We need to check if it improves their lives. We need them to get in a situation where they are able to choose what to do with their lives. Not from equally bad situations, but giving people the possibility to make their live become good.</p> <p>We need to understand the problems of those countries. We have to work with the people there, not work for them. We have to support, not to lead.</p> <p>There are certainly a lot of organizations like <a href="https://en.wikipedia.org/wiki/Engineers_Without_Borders">Engineers Without Borders</a> and <a href="https://en.wikipedia.org/wiki/M%C3%A9decins_Sans_Fronti%C3%A8res">Doctors Without Borders</a> which have a very good idea what has to be done in a short-term perspective to improve the lives of many people. However, we should plan for a long-term perspective. We should get in contact with refugees who are willing to get back if the situation was better and try to figure out what they need to improve the situation.</p> <p>And we should finally stand to our word and reach the <a href="https://en.wikipedia.org/wiki/Millennium_Development_Goals">Millennium Development Goals</a> I can’t find the source, but the costs for reaching the MDGs were lower than I expected. Especially access to clean water significantly lower than 20 Billion US-Dollar, if I remember it correctly. The GDP of Europe is about 18,527,116 Million US-Dollar. That means we would have to spend about 0.1 % of our GDP for this goal. Now think of the money that was spend in the <a href="https://en.wikipedia.org/wiki/European_debt_crisis">European debt crisis</a>. It is hard to put numbers on here, but it was much more than 18 Billion US-Dollar.</p> <h2 id="hypocracy">Hypocracy</h2> <p>A fellow student recently pointed out that there were also <a href="https://en.wikipedia.org/wiki/2015_Beirut_bombings">2015 Beirut bombings</a>. I didn’t even see that in the news. A lot of people die preventable deaths due to the lack of access to clean water, sanitation and food. And we don’t even talk about the MDGs. Not really.</p> <h2 id="some-final-words">Some final words</h2> <p>One main point of this mini-article is that I am pretty sure people will react to fast. No matter what we do, we should think about it thoroughly. This article is - like hundreds of blog articles, quite a bit of “professional” journalist articles and surely some statements by politicians - not well investigated. It is only a quick, spontaneous reaction.</p> <p>The other important point is that we have alternatives to more military and surveillance spendings. We should really think about that. We should talk about it and evaluate it. Finally, it the question is: In which kind of society do we want to live?</p> <h2 id="edit-the-reaction">Edit: The reaction</h2> <p>Now it seems to be clear how most politicians react:</p> <ul> <li><a href="http://www.euractiv.de/sections/eu-innenpolitik/valls-greift-auch-anderen-europaeische-laender-319509">Frankreichs Premier Valls: IS greift auch andere europäische Länder an</a></li> <li><a href="http://www.euractiv.de/sections/eu-aussenpolitik/franzoesisches-militaer-bombardiert-stellungen-syrien-319501">Französisches Militär bombardiert IS-Stellungen in Syrien</a></li> <li><a href="http://www.euractiv.de/sections/eu-innenpolitik/sicherheitsmassnahmen-deutschland-deutlich-verschaerft-319497">Sicherheitsmaßnahmen in Deutschland deutlich verschärft</a></li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="https://www.youtube.com/watch?v=SGD2q2vewzQ">Du bist Terrorist</a>: A clip by a German satire show.</li> <li>Recent French military actions: <ul> <li><a href="https://en.wikipedia.org/wiki/2011_military_intervention_in_Libya">2011 military intervention in Libya</a></li> <li><a href="https://en.wikipedia.org/wiki/French_forces_in_Afghanistan">French forces in Afghanistan</a></li> <li><a href="https://en.wikipedia.org/wiki/Northern_Mali_conflict">Northern Mali conflict</a></li> <li><a href="https://en.wikipedia.org/wiki/War_on_Terror">War on Terror</a></li> </ul> </li> <li>Euractiv (German) <ul> <li><a href="http://www.euractiv.de/sections/eu-innenpolitik/terror-paris-hollande-spricht-von-kriegsakt-des-319482">Terror in Paris: Hollande spricht von “Kriegsakt des IS”</a></li> <li><a href="http://www.euractiv.de/sections/eu-innenpolitik/anschlagserie-paris-hollande-verhaengt-ausnahmezustand-fuer-ganz-frankreich">Anschlagserie in Paris: Hollande verhängt Ausnahmezustand für ganz Frankreich</a></li> <li><a href="http://www.euractiv.de/sections/eu-innenpolitik/terror-ueberschattet-frankreich-mehr-als-hundert-tote-paris-319479">Terror in Paris: Attentäter nennen als Grund Frankreichs Syrien-Politik</a></li> </ul> </li> </ul> Tensor Flow - A quick impression //martin-thoma.com/tensor-flow-quick/ Wed, 11 Nov 2015 22:33:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/tensor-flow-quick <p>Tensor Flow is a machine learning toolkit which recently got published by Google. They published it under <a href="https://tldrlegal.com/license/apache-license-2.0-(apache-2.0)">Apache License 2.0</a>. Looking at the source code overview, it seems to be mainly C++ with a significant bit of Python.</p> <p>I guess the abstract of the <a href="http://download.tensorflow.org/paper/whitepaper2015.pdf">Whitepaper</a> is a good description what TensorFlow is:</p> <blockquote> <p>TensorFlow is an interface for expressing machine learning algorithms, and an implementation for executing such algorithms. A computation expressed using TensorFlow can be executed with little or no change on a wide variety of heterogeneous systems, ranging from mobile devices such as phones and tablets up to large-scale distributed systems of hundreds of machines and thousands of computational devices such as GPU cards. The system is flexible and can be used to express a wide variety of algorithms, including training and inference algorithms for deep neural network models, and it has been used for conducting research and for deploying machine learning systems into production across more than a dozen areas of computer science and other fields, including speech recognition, computer vision, robotics, information retrieval, natural language processing, geographic information extraction, and computational drug discovery. This paper describes the TensorFlow interface and an implementation of that interface that we have built at Google. The TensorFlow API and a reference implementation were released as an open-source package under the Apache 2.0 license in November, 2015 and are available at www.tensorflow.org.</p> </blockquote> <p>The core seems to be written in C++, but it has a Python front end.</p> <p>By now, I couldn’t test much because I just made my GPU machine unusable (while trying to get the GPU General Computing practical software to run…). I’ll try to expand this article as soon as possible, but I guess it might take several weeks until I have enough time. Lets see…</p> <h2 id="installation">Installation</h2> <p>The documentation about the installation makes a VERY good impression. Better than anything I can write in a few minutes, so … <a href="http://tensorflow.org/get_started/os_setup.md">RTFM</a> 😜</p> <p>For Linux systems with CUDA and without root privileges, you can install it with:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pip install https://storage.googleapis.com/tensorflow/linux/gpu/tensorflow-0.5.0-cp27-none-linux_x86_64.whl --user </pre></div> </div> </div> <p>But remember you have to set the environment variable <code>LD_LIBRARY_PATH</code> and <code>CUDA_HOME</code>. For many configurations, adding the following lines to your <code>.bashrc</code> will work:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>export LD_LIBRARY_PATH=&quot;$LD_LIBRARY_PATH:/usr/local/cuda/lib64&quot; export CUDA_HOME=/usr/local/cuda </pre></div> </div> </div> <h2 id="mnist">MNIST</h2> <p>The following code can be used to check if your Tensor Flow installation is working. You have to have the <a href="https://gist.github.com/MartinThoma/f37150d0c521f598b08a"><code>get_mnist_data_tf.py</code></a> in the same directory as the following script. I’ve - more or less - directly copied it from <a href="http://tensorflow.org/tutorials/mnist/pros/index.md">the tutorial</a>. Just execute the script below and see if it finishes without throwing errors.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">get_mnist_data_tf</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">read_data_sets</span> mnist = read_data_sets(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">MNIST_data/</span><span style="color:#710">&quot;</span></span>, one_hot=<span style="color:#069">True</span>) <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">tensorflow</span> <span style="color:#080;font-weight:bold">as</span> tf sess = tf.InteractiveSession() x = tf.placeholder(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">float</span><span style="color:#710">&quot;</span></span>, shape=[<span style="color:#069">None</span>, <span style="color:#00D">784</span>]) y_ = tf.placeholder(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">float</span><span style="color:#710">&quot;</span></span>, shape=[<span style="color:#069">None</span>, <span style="color:#00D">10</span>]) W = tf.Variable(tf.zeros([<span style="color:#00D">784</span>,<span style="color:#00D">10</span>])) b = tf.Variable(tf.zeros([<span style="color:#00D">10</span>])) sess.run(tf.initialize_all_variables()) y = tf.nn.softmax(tf.matmul(x,W) + b) cross_entropy = -tf.reduce_sum(y_*tf.log(y)) train_step = tf.train.GradientDescentOptimizer(<span style="color:#60E">0.01</span>).minimize(cross_entropy) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">1000</span>): batch = mnist.train.next_batch(<span style="color:#00D">50</span>) train_step.run(feed_dict={x: batch[<span style="color:#00D">0</span>], y_: batch[<span style="color:#00D">1</span>]}) correct_prediction = tf.equal(tf.argmax(y,<span style="color:#00D">1</span>), tf.argmax(y_,<span style="color:#00D">1</span>)) accuracy = tf.reduce_mean(tf.cast(correct_prediction, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">float</span><span style="color:#710">&quot;</span></span>)) print(accuracy.eval(feed_dict={x: mnist.test.images, y_: mnist.test.labels})) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">weight_variable</span>(shape): initial = tf.truncated_normal(shape, stddev=<span style="color:#60E">0.1</span>) <span style="color:#080;font-weight:bold">return</span> tf.Variable(initial) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">bias_variable</span>(shape): initial = tf.constant(<span style="color:#60E">0.1</span>, shape=shape) <span style="color:#080;font-weight:bold">return</span> tf.Variable(initial) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">conv2d</span>(x, W): <span style="color:#080;font-weight:bold">return</span> tf.nn.conv2d(x, W, strides=[<span style="color:#00D">1</span>, <span style="color:#00D">1</span>, <span style="color:#00D">1</span>, <span style="color:#00D">1</span>], padding=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">SAME</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">max_pool_2x2</span>(x): <span style="color:#080;font-weight:bold">return</span> tf.nn.max_pool(x, ksize=[<span style="color:#00D">1</span>, <span style="color:#00D">2</span>, <span style="color:#00D">2</span>, <span style="color:#00D">1</span>], strides=[<span style="color:#00D">1</span>, <span style="color:#00D">2</span>, <span style="color:#00D">2</span>, <span style="color:#00D">1</span>], padding=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">SAME</span><span style="color:#710">'</span></span>) W_conv1 = weight_variable([<span style="color:#00D">5</span>, <span style="color:#00D">5</span>, <span style="color:#00D">1</span>, <span style="color:#00D">32</span>]) b_conv1 = bias_variable([<span style="color:#00D">32</span>]) x_image = tf.reshape(x, [-<span style="color:#00D">1</span>,<span style="color:#00D">28</span>,<span style="color:#00D">28</span>,<span style="color:#00D">1</span>]) h_conv1 = tf.nn.relu(conv2d(x_image, W_conv1) + b_conv1) h_pool1 = max_pool_2x2(h_conv1) W_conv2 = weight_variable([<span style="color:#00D">5</span>, <span style="color:#00D">5</span>, <span style="color:#00D">32</span>, <span style="color:#00D">64</span>]) b_conv2 = bias_variable([<span style="color:#00D">64</span>]) h_conv2 = tf.nn.relu(conv2d(h_pool1, W_conv2) + b_conv2) h_pool2 = max_pool_2x2(h_conv2) W_fc1 = weight_variable([<span style="color:#00D">7</span> * <span style="color:#00D">7</span> * <span style="color:#00D">64</span>, <span style="color:#00D">1024</span>]) b_fc1 = bias_variable([<span style="color:#00D">1024</span>]) h_pool2_flat = tf.reshape(h_pool2, [-<span style="color:#00D">1</span>, <span style="color:#00D">7</span>*<span style="color:#00D">7</span>*<span style="color:#00D">64</span>]) h_fc1 = tf.nn.relu(tf.matmul(h_pool2_flat, W_fc1) + b_fc1) keep_prob = tf.placeholder(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">float</span><span style="color:#710">&quot;</span></span>) h_fc1_drop = tf.nn.dropout(h_fc1, keep_prob) W_fc2 = weight_variable([<span style="color:#00D">1024</span>, <span style="color:#00D">10</span>]) b_fc2 = bias_variable([<span style="color:#00D">10</span>]) y_conv = tf.nn.softmax(tf.matmul(h_fc1_drop, W_fc2) + b_fc2) cross_entropy = -tf.reduce_sum(y_*tf.log(y_conv)) train_step = tf.train.AdamOptimizer(<span style="color:#60E">1e-4</span>).minimize(cross_entropy) correct_prediction = tf.equal(tf.argmax(y_conv,<span style="color:#00D">1</span>), tf.argmax(y_,<span style="color:#00D">1</span>)) accuracy = tf.reduce_mean(tf.cast(correct_prediction, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">float</span><span style="color:#710">&quot;</span></span>)) sess.run(tf.initialize_all_variables()) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">1000</span>): batch = mnist.train.next_batch(<span style="color:#00D">50</span>) <span style="color:#080;font-weight:bold">if</span> i%<span style="color:#00D">100</span> == <span style="color:#00D">0</span>: train_accuracy = accuracy.eval(feed_dict={ x:batch[<span style="color:#00D">0</span>], y_: batch[<span style="color:#00D">1</span>], keep_prob: <span style="color:#60E">1.0</span>}) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">step %d, training accuracy %g</span><span style="color:#710">&quot;</span></span>%(i, train_accuracy)) train_step.run(feed_dict={x: batch[<span style="color:#00D">0</span>], y_: batch[<span style="color:#00D">1</span>], keep_prob: <span style="color:#60E">0.5</span>}) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">test accuracy %g</span><span style="color:#710">&quot;</span></span>%accuracy.eval(feed_dict={ x: mnist.test.images, y_: mnist.test.labels, keep_prob: <span style="color:#60E">1.0</span>})) </pre></div> </div> </div> <h2 id="observations">Observations</h2> <p>While looking at the MNIST example, I made a couple of observations. Let’s begin with the nice parts:</p> <ul> <li>Tensor Flow has a usable documentation (e.g. <a href="http://tensorflow.org/api_docs/python/nn.md">The neural network part</a>). Not great, as Lasagne where you have lots of details (e.g. <a href="http://lasagne.readthedocs.org/en/latest/modules/nonlinearities.html#lasagne.nonlinearities.sigmoid">activation functions</a>)</li> <li>Seems to be quite easy to use.</li> <li>Seems to be well-tested by simply being used in many different projects by Google.</li> <li>Just like Theano (and thus Lasagne), Tensor flow has automatic differenciation.</li> </ul> <p>Not sure:</p> <ul> <li>How easy is it to share trained models? In which format would you do so?</li> <li>How easy is it to understand a shared model?</li> <li>How easy is it to get something new to Tensor Flow like recurrent layers? (Actually, this seems rather to show that either the Whitepaper is a bit misleading or the documentation / Google search is not that good. In the whitepaper they write something about LTSM models, but I couldn’t find any docs about that. Only by manually going through the manual, <a href="http://tensorflow.org/tutorials/recurrent/index.md">I found it</a>)</li> </ul> <p>Not so nice:</p> <ul> <li>Doesn’t work with Python 3.</li> <li>They don’t follow <a href="https://www.python.org/dev/peps/pep-0008/">PEP8</a>. I know that there is a <a href="https://google.github.io/styleguide/pyguide.html">Python style guide by Google</a>, but it does not seem to follow that one either. See the next section for some more detailed feedback.</li> <li>Just like the other Toolkits, you need CUDA. It doesn’t work with OpenCL.</li> </ul> <h3 id="pep8">PEP8</h3> <ul> <li>Whitespace <ul> <li><code>W = tf.Variable(tf.zeros([784,10]))</code> should be <code>W = tf.Variable(tf.zeros([784, 10]))</code>. Missing whitespaces happened quite often.</li> <li>Indent with 2 spaces instead of 4 spaces. The Google guide seems also to use 4 (<a href="W = tf.Variable(tf.zeros([784,10]))">example</a>).</li> <li>Newlines between functions are missing.</li> </ul> </li> <li>Print statement instead of a print function was used &amp;rightarrow; only Python 2, not Python 3.</li> <li>I’m not sure why <code>y_</code> has the trailing underscore. According to <a href="https://www.python.org/dev/peps/pep-0008/#descriptive-naming-styles">PEP8</a>, a single trailing underscore is used by convention to avoid conflicts with Python keyword.</li> <li>A mixture of different styles as pointed out on <a href="http://beust.com/weblog/2015/11/09/tensorflows-rough-exterior/">Credric’s Blog</a></li> </ul> <h2 id="videos">Videos</h2> <iframe width="512" height="288" src="https://www.youtube-nocookie.com/embed/oZikw5k_2FM?rel=0" frameborder="0" allowfullscreen=""></iframe> <p>Starting at 21m 2s:</p> <iframe width="512" height="288" src="https://www.youtube-nocookie.com/embed/90-S1M7Ny_o?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="alternatives--similar-software">Alternatives / Similar software</h2> <p>As I don’t really know by now what Tensor Flow is doing, I can’t pin-point alternatives. But I have some educated guesses:</p> <ul> <li><a href="http://deeplearning.net/software/theano/">Theano</a> has been around for quite a while and seems to have a similar approach with its computational graph. Enhanced by <a href="http://lasagne.readthedocs.org/en/latest/">Lasagne</a>, it is a pretty good alternative when it comes to neural networks. Lasagne has an exceptionally good documentation, but parts of the tutorial could still be improved.</li> <li><a href="http://caffe.berkeleyvision.org/">Caffe</a> was something I recently tried. I didn’t like it too much due to the lack of documentation, but it certainly is a big project. Especially when it comes to images.</li> <li>I haven’t tried, but they look promising: <ul> <li><a href="http://chainer.org/">Chainer</a></li> <li><a href="http://mxnet.readthedocs.org/en/latest/">MXNet</a></li> <li><a href="http://rll.berkeley.edu/cgt/">CGT</a></li> <li><a href="http://torch.ch/">Torch</a> has a very nice example for <a href="http://karpathy.github.io/2015/05/21/rnn-effectiveness/">a character predictor</a>.</li> </ul> </li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="http://tensorflow.org/">Official Website</a> <ul> <li><a href="https://github.com/tensorflow/tensorflow">github.com/tensorflow</a></li> <li><a href="http://download.tensorflow.org/paper/whitepaper2015.pdf">TensorFlow: Large-Scale Machine Learning on Heterogeneous Distributed Systems</a></li> </ul> </li> <li><a href="https://news.ycombinator.com/item?id=10532957">news.ycombinator.com</a></li> <li><a href="https://www.reddit.com/r/programming/comments/3s4vkn/google_brains_deep_learning_library_tensorflow_is/">reddit.com/r/programming</a></li> </ul> Machine Learning 1 //martin-thoma.com/machine-learning-1-course/ Mon, 09 Nov 2015 16:02:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/machine-learning-1-course <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Machine Learning 1&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://www.fzi.de/wir-ueber-uns/organisation/mitarbeiter/address/39/?no_cache=1">Herrn Prof. Dr. Zöllner</a> im Wintersemester 2014/2015 gehört.<br />Es gibt auch einen Artikel über <a href="//martin-thoma.com/machine-learning-2-course/">Machine Learning 2</a></div> <h2 id="folien">Folien</h2> <h3 id="einordnungskriterien">Einordnungskriterien</h3> <p>Slide name: <code>ML-Einordnungskriterien.pdf</code></p> <table class="table"> <thead> <tr> <th rowspan="2" colspan="2">Algorithmus</th> <th colspan="2" style="text-align: center; border-right: solid;">Inferenztyp</th> <th colspan="2" style="text-align: center; border-right: solid;">Lernebene</th> <th colspan="2" style="text-align: center; border-right: solid;">Lernvorgang</th> <th colspan="2" style="text-align: center; border-right: solid;">Beispielgebung</th> <th colspan="2" style="text-align: center; border-right: solid;">Beispielumfang</th> <th colspan="2" style="text-align: center;">Hintergrundwissen</th> </tr> <tr> <td style="text-align: center;"><abbr title="induktiv">ind.</abbr></td> <td style="text-align: center; border-right: solid;"><abbr title="deduktiv">ded.</abbr></td> <td style="text-align: center;"><abbr title="symbolisch">symb.</abbr></td> <td style="text-align: center; border-right: solid;"><abbr title="subsymbolisch">subsymb.</abbr></td> <td style="text-align: center;">&uuml;berwacht</td> <td style="text-align: center; border-right: solid;"><abbr title="unüberwacht">un&uuml;b.</abbr></td> <td style="text-align: center;"><abbr title="inkrementell">inkr.</abbr></td> <td style="text-align: center; border-right: solid;"><abbr title="nicht inkrementell">nicht inkr.</abbr></td> <td style="text-align: center;">gering</td> <td style="text-align: center; border-right: solid;">gro&szlig;</td> <td style="text-align: center;"><abbr title="empirisch">emp.</abbr></td> <td style="text-align: center;"><abbr title="axiomatisch">axio.</abbr></td> </tr> </thead> <tbody> <tr> <td colspan="2"><abbr title="k nearest neighbor"><span>\(k\)</span>-NN</abbr></td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2"><abbr title="Support Vector Machines"><a href="#svm">SVMs</a></abbr></td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="1" rowspan="2"><a href="#decision-trees">Decision Trees</a></td> <td>ID3</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td>ID5R</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="1" rowspan="2"><abbr title="neuronale Netze">NN</abbr></td> <td>klassisch</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td>Auto-Encoder</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2">Bayessche Netze</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2"><abbr title="Hidden Markov Models"><a href="#hmm">HMMs</a></abbr></td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2">Version-Space Algorithmus</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2">Specific-to-General Konzeptlernen</td> <td style="text-align: center;">?</td> <td style="text-align: center; border-right: solid;">?</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">?</td> <td style="text-align: center; border-right: solid;">?</td> <td style="text-align: center;">?</td> <td style="text-align: center; border-right: solid;">?</td> <td style="text-align: center;">?</td> <td style="text-align: center; border-right: solid;">?</td> <td style="text-align: center;">?</td> <td style="text-align: center;">?</td> </tr> <tr> <td colspan="2">k-means clustering</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2">AHC</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2">COBWEB</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2">CBR</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center;">&nbsp;</td> </tr> <tr> <td colspan="2"><abbr title="Erklärungsbasierte Generalisierung">EBG</abbr></td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center; border-right: solid;">x</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">x</td> <td style="text-align: center; border-right: solid;">&nbsp;</td> <td style="text-align: center;">&nbsp;</td> <td style="text-align: center;">x</td> </tr> </tbody> </table> <h3 id="einfhrung">Einführung</h3> <p>Slide name: <code>MLI_01_Einfuehrung_slides1.pdf</code></p> <ul> <li>Was ist Intelligenz? (Problemlösen, Erinnern, Sprache, Kreativität, Bewusstsein, Überleben in komplexen Welten, )</li> <li>Wissensrepräsentation: <ul> <li>Assoziierte Paare (Eingangs- und Ausgangsvariablen)</li> <li>Entscheidungsbäume (Klassen diskriminieren)</li> <li>Parameter in algebraischen ausdrücken</li> <li>Formale Grammatiken</li> <li>Logikbasierte Ausdrücke</li> <li>Taxonomien</li> <li>Semantische Netze</li> <li>Markov-Ketten</li> </ul> </li> </ul> <dl> <dt><dfn>Machine Learning</dfn> von Tom Mitchell</dt> <dd>A computer program is said to learn from experience E with respect to some class of tasks T and performance measure P, if its performance at tasks in T, as measured by P, improves with experience E.</dd> <dt><dfn>Deduktion</dfn></dt> <dd>Die Deduktion ist eine Schlussfolgerung von gegebenen Prämissen auf die logisch zwingenden Konsequenzen. Deduktion ist schon bei Aristoteles als „Schluss vom Allgemeinen auf das Besondere“ verstanden worden.</dd> <dt><dfn>Modus ponens</dfn></dt> <dd>Der Modus ponens ist eine Art des logischen Schließens. Er besagt: Wenn die Prämissen \(A \rightarrow B\) und \(A\) gelten, dann gilt auch \(B\).</dd> <dt><dfn>Abduktion</dfn> by Peirce</dt> <dd>Deduction proves that something must be; Induction shows that something actually is operative; Abduction merely suggests that something may be.</dd> </dl> <h3 id="induktives-lernen">Induktives Lernen</h3> <p>Slide name: <code>MLI_02_InduktivesLernen_slides1.pdf</code></p> <dl> <dt><dfn>Version Space</dfn></dt> <dd>Der Raum aller Hypotesen, welche mit den Trainingsbeispielen konsistent sind.</dd> <dt><dfn>Version Space Algorithmus</dfn></dt> <dd>Der Version Space Algorithmus ist ein binärer Klassifikator für diskrete Feature-Spaces. Er startet mit der generellsten Hypothese \(G = (?, \dots, ?)\) - alles ist wahr - und der speziellsten Hypothese \(S = (\#, \dots, \#)\) - nichts ist wahr. Wenn ein Beispiel mit dem Label <code>true</code> gesehen wird, dann wird die speziellste Hypothese angepasst und veralgemeinert. Wenn ein Beispiel mit dem Label <code>false</code> gesehen wird, wird die generellste Hypothese spezialisiert.<br /> So kann man den Raum aller mit den Trainingsdaten konsistenten Hypothesen finden.</dd> <dt><dfn>Konzept</dfn></dt> <dd>Ein <i>Konzept</i> beschreibt eine Untermenge von Objekten oder Ereignissen definiert auf einer größerer Menge.</dd> <dt><dfn>Konsistenz</dfn></dt> <dd>Keine negativen Beispiele werden positiv klassifiziert.</dd> <dt><dfn>Vollständigkeit</dfn></dt> <dd>Alle positiven Beispiele werden als positiv klassifiziert.</dd> </dl> <ul> <li>Algorithmen: Bäume (Wälder?) <ul> <li>Suche vom Allgemeinen zum Speziellen: Negative Beispiele führen zur Spezialisierung</li> <li>Suche vom Speziellen zum Allgemeinen: Positive Beispiele führen zur Verallgemeinerung</li> <li><a href="https://de.wikipedia.org/wiki/Versionsraum">Version Space</a>: Beides gleichzeitig anwenden</li> </ul> </li> <li>Präzendenzgraphen: In welcher Reihenfolge werden Aktionen ausgeführt?</li> </ul> <p>Version Space Algorithmus ist:</p> <ul> <li>Induktiver Inferenztyp</li> <li>Symbolische Ebene des Lernens</li> <li>Überwachtes Lernen</li> <li>Inkrementelle Beispielgebung</li> <li>Umfangreich (viele Beispiele)</li> <li>Empirisches Hintergrundwissen</li> <li>Voraussetzungen: Konsistente Beispiele, korrekte Hypothese im Hypothesenraum</li> <li>Positive Aspekte: <ul> <li>Es ist feststellbar, welche Art von Beispielen noch nötig ist</li> <li>Es ist feststellbar, wann das Lernen abgeschlossen ist</li> </ul> </li> </ul> <p>Weiteres</p> <dl> <dt><dfn>Inductive bias</dfn></dt> <dd>Induktives Lernen benötigt Vorannahmen.</dd> <dt><dfn>Bias</dfn> ("Vorzugskriterium")</dt> <dd>Vorschrift, nach der Hypothese gebildet werden.</dd> </dl> <h3 id="reinforcement-learning">Reinforcement Learning</h3> <p>Slide name: <code>MLI_03_ReinforcementLearning_slides1.pdf</code></p> <p>Siehe auch:</p> <ul> <li><a href="../neuronale-netze-vorlesung/#tocAnchor-1-1-9">Neuronale Netze</a></li> <li><a href="../machine-learning-2-course/#tocAnchor-1-1-5">Machine Learning 2</a></li> <li><a href="https://github.com/MartinThoma/cat-vs-mouse">Cat vs. Mouse code</a></li> <li>Berkeley <ul> <li>CS188 Intro to AI: <a href="http://ai.berkeley.edu/reinforcement.html">Project 3: Reinforcement Learning</a></li> <li>Dan Klein, Pieter Abbeel: <a href="https://www.youtube.com/watch?v=w33Lplx49_A">Lecture 10: Reinforcement Learning</a> on YouTube. University of California, Berkeley. This expalins TD-learning.</li> </ul> </li> <li><a href="http://datascience.stackexchange.com/q/9832/8820">What is the Q function and what is the V function in reinforcement learning?</a></li> </ul> <dl> <dt><a href="https://de.wikipedia.org/wiki/Markow-Entscheidungsproblem"><dfn>Markovsches Entscheidungsproblem</dfn></a> (<dfn>Markov Decision Process</dfn>, <dfn>MDP</dfn>)</dt> <dd>Ein Markovsches Entscheidungsproblem ist ein 5-Tupel \(S, A, P, R, \gamma\) mit: <ul> <li>\(S\): Endliche Zustandsmenge (states)</li> <li>\(A(s)\): Die Menge von möglichen Aktionen im Zustand \(s\)</li> <li>\(P(s, s', a) = P(s_{t+1} = s' | s_t = s, a_t = a)\): Die Wahrscheinlichkeit im Zeitschritt \(t+1\) im Zustand \(s'\) zu sein, wenn man zum Zeitpunkt \(t\) im Zustand \(s\) ist und die Aktion \(a\) ausführt</li> <li>\(R(s, s', a) \in \mathbb{R}\): Die direkte Belohnung, wenn durch die Aktion \(a\) vom Zustand \(s\) in den Zustand \(s'\) gekommen ist.</li> <li>\(\gamma \in [0, 1]\): Der Diskontierungsfaktor, welche die Bedeutung von direkten Belohnungen im Vergleich zu künftigen Belohnungen anzeigt.</li> </ul></dd> <dt><a href="https://en.wikipedia.org/wiki/Reinforcement_learning"><dfn>Reinforcement Learning</dfn></a> (<dfn>RL</dfn>, <dfn><a href="https://de.wikipedia.org/wiki/Best%C3%A4rkendes_Lernen">Bestärkendes Lernen</a></dfn>)</dt> <dd>Beim bestärkenden Lernen liegt ein Markow-Entscheidungsproblemen vor. Es gibt also einen Agenten, der Aktionen ausführen kann. Diese können (nicht notwendigerweise sofort) bewertet werden.</dd> <dt><dfn>Policy</dfn></dt> <dd>Eine <b>policy \(\pi: S \rightarrow A\)</b> ist die Vorschrift, in welchem Zustand welche Aktion ausgeführt werden soll.</dd> <dt><dfn>Policy Learning</dfn></dt> <dd>Unter <i>Policy Learning</i> versteht man die Suche nach einer optimalen Policy \(\pi^*\).</dd> <dt><dfn>Value-Funktion</dfn></dt> <dd>Die Funktion \(V^\pi: S \rightarrow \mathbb{R}\) heißt Value-Funktion. Sie gibt den erwarteten Wert (nicht die Belohnung, da bei der V-Funktion noch der Diskontierungsfaktor eingeht!) eines Zustands \(s\) unter der policy \(\pi\) an. Mit \(V^*\) wird der Wert unter der optimalen policy bezeichnet.</dd> <dt><dfn>Q-Funktion</dfn></dt> <dd>Die Funktion \(Q^\pi: S \times A \rightarrow \mathbb{R}\) gibt den erwarteten Wert einer eines Zustandes \(s\) unter der policy \(\pi\), wenn die Aktion \(a\) ausgeführt wird an. Es gilt: \[Q^\pi(s, \pi(s)) = V^\pi(s)\]</dd> <dt><a name="rl-eligibility-trace"></a><dfn>Eligibility Traces</dfn></dt> <dd>Die Idee scheint einfach zu sein, dass man ein späteres Update auch auf frühere Ereignisse "zurückpropagiert". TODO See also: <a href="https://webdocs.cs.ualberta.ca/~sutton/book/ebook/node72.html">Reinforcement Learning: An Introduction</a> by Sutton. </dd> </dl> <ul> <li>Beispiel für RL: Roboter muss zu einem Ziel navigieren</li> </ul> <p>Algorithmen:</p> <dl> <dt><dfn>Simple Value Iteration</dfn></dt> <dd>Simple Value Iteration estimates the value function by updating it as long as necessary to converge: \[\hat{V}^*(s_t) \leftarrow r_t + \gamma \hat{V}^*(s_{t+1})\] "Simple" means that the transition function is deterministic. <!-- In the non-deterministic case the update rule is \[\hat{V}^*(s_t) \leftarrow r_t + \gamma E(\hat{V}^*(s_{t+1}))\] --> It is explained in <ul> <li>Sebastian Thrun: <a href="https://www.youtube.com/watch?v=oefOCk3koZo">Unit 9 17 Value Iteration 1</a> on YouTube.</li> <li>Sebastian Thrun: <a href="https://www.youtube.com/watch?v=8-pzJXUiXrM">Unit 9 17 Value Iteration 2</a> on YouTube.</li> <li>Sebastian Thrun: <a href="https://www.youtube.com/watch?v=glHKJ359Cnc">Unit 9 17 Value Iteration 3</a> on YouTube.</li> </ul> </dd> <dt><dfn>Simple Temporal Difference Learning</dfn></dt> <dd>Simple Temporal Difference Learning is just like Simple Value Iteration, but now the Value function is updated with a learning rate \(\alpha\): \[\hat{V}^*(s_t) \leftarrow (1-\alpha) \cdot \hat{V}^*(s_t) + \alpha(r_t + \gamma \hat{V}^*(s_{t+1}))\] Mehr dazu im <a href="#td-learning">nächsten Abschnitt</a>. </dd> <dt><dfn>Q-Learning</dfn></dt> <dd>Siehe <a href="#q-learning">nächster Abschnitt</a></dd> <dt><a href="https://en.wikipedia.org/wiki/State-Action-Reward-State-Action"><dfn>SARSA</dfn></a> (<dfn>State-Action-Reward-State-Action</dfn>)</dt> <dd>SARSA is a learning algorithm which updates the Q-function: \[Q(s_t,a_t) \leftarrow (1-\alpha) \cdot Q(s_t,a_t) + \alpha [r_{t+1} + \gamma Q(s_{t+1}, a_{t+1})]\] where \(\alpha \in (0, 1)\) is the learning rate and \(\gamma \in [0, 1]\) is the discount factor. </dd> <dt><dfn>SARSA(\(\lambda\))</dfn></dt> <dd>SARSA(\(\lambda\)) ist SARSA mit Eligibility Traces. TODO </dd> </dl> <h4 id="q-learning">Q-Learning</h4> <ul> <li><a href="https://en.wikipedia.org/wiki/Q-learning">Q-learning</a> <ul> <li><a href="https://www.youtube.com/watch?v=yS5F_vm9Ahk">YouTube: Lecture 18: RL Part 1: Q-Learning</a>: 1:16:11. BrownCS141 Spring 2014.</li> <li><a href="https://www.youtube.com/watch?v=3sLV0OJLdns">YouTube: PacMan</a></li> </ul> </li> </ul> <p>Pseudocode:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>initialize Q[num_states, num_actions] start in state s repeat: select and execute action a r ← R(s, a) # Receive reward s' ← T(s, a) # Get on new state Q[s', a] ← (1- α) * Q[s, a] + α * (r + γ max_{a'} Q[s', a']) s ← s' </pre></div> </div> </div> <p>where \(\alpha \in (0, 1]\) is a learning rate and \(\gamma\) is a discount factor.</p> <p>See also:</p> <ul> <li><a href="https://www.youtube.com/watch?v=ntZ0Hc1_LsY">Mario Q-learning</a> on YouTube. 2010.</li> </ul> <h4 id="td-learning">TD-Learning</h4> <ul> <li>R. Sutton und A. Barto: <a href="https://webdocs.cs.ualberta.ca/~sutton/book/ebook/node60.html">Temporal-Difference Learning</a>. 1998.</li> </ul> <p>Der TD-Learning Algorithmus beschäftigt sich mit dem Schätzen der Value-Funktion \(V^\pi\) für eine gegebene Policy \(\pi\). Das wird auch <i>policy evaluation</i> oder <i>prediction</i> genannt.</p> <ul> <li><a href="https://de.wikipedia.org/wiki/Temporal_Difference_Learning">TD-Learning</a> (Temporal Difference Learning)</li> </ul> <h4 id="siehe-auch">Siehe auch</h4> <ul> <li><a href="https://de.wikipedia.org/wiki/Optimalit%C3%A4tsprinzip_von_Bellman">Optimalitätsprinzip von Bellman</a></li> <li>Guest Post (Part I): <a href="http://www.nervanasys.com/demystifying-deep-reinforcement-learning/">Demystifying Deep Reinforcement Learning</a></li> </ul> <h3 id="lerntheorie">Lerntheorie</h3> <p>Slide name: <code>MLI_04_Lerntheorie_slides1.pdf</code></p> <dl> <dt><dfn>Ockhams Rasiermesser</dfn> (Quelle: <a href="https://de.wikipedia.org/wiki/Ockhams_Rasiermesser">Wikipedia</a>)</dt> <dd>Von mehreren möglichen Erklärungen für ein und denselben Sachverhalt ist die einfachste Theorie allen anderen vorzuziehen. Eine Theorie ist einfach, wenn sie möglichst wenige Variablen und Hypothesen enthält, und wenn diese in klaren logischen Beziehungen zueinander stehen, aus denen der zu erklärende Sachverhalt logisch folgt.</dd> <dt><a href="https://en.wikipedia.org/wiki/Structural_risk_minimization"><dfn>Structural Risc Minimization</dfn></a> (<dfn>SRM</dfn>)</dt> <dd>Unter <i>Structural risk minimization</i> versteht man die Abwägung zwischen einem einfachen Modell und einem komplexen Modell, welches auf den Trainingsdaten besser funktioniert aber eventuell mehr unter Overfitting leidet.</dd> <dt><dfn>Vapnik-Chervonenkis Dimension</dfn> (<dfn>VC-Dimension</dfn>)</dt> <dd>Die <abbr title="Vapnik-Chervonenkis">VC</abbr>-Dimension \(VC(H, X) \in \mathbb{N} \cup \infty\) eines Hypothesenraumes \(H\) ist gleich der maximalen Anzahl an Datenpunkten aus \(X\), die von \(H\) beliebig in zwei Mengen gespalten werden können. Dabei muss es nur eine Teilmenge \(X' \subseteq X \) der Größe \(n\) geben, damit \(VC(H, X) \geq n\) gilt. Falls beliebige Teilmengen von \(X\) durch \(H\) separiert werden können, so gilt \(VC(H, X) = \infty\). Praktisch gesehen ist \(X\), die Menge aller möglichen Features, sowie \(H\), die Menge aller möglichen Trennlinien im Feature-Space, vorgegeben. Die Frage ist ob man eine Teilmenge \(X' \subseteq X\) findet mit \(|X'| = n\), sodass man für \(X'\) jede Mögliche Teilung in zwei Mengen durch \(H\) realisieren kann.</dd> <dt><a href="https://en.wikipedia.org/wiki/Probably_approximately_correct_learning">Probably approximately correct learning</a> (<dfn>PAC</dfn>)</dt> <dd>PAC macht eine Aussage über die Anzahl der benötigten Stichproben, wenn man einen bestimmten realen Fehler mit einer frei zu wählenden Wahrscheinlichkeit bekommen will.</dd> </dl> <ul> <li>Lernmaschine wird definiert durch Hypothesenraum \({h_\alpha: \alpha \in A}\) und Lernverfahren. Das Lernverfahren ist die Methode um \(\alpha_{\text{opt}}\) mit Hilfe von Lernbeispielen zu finden.</li> <li>Probleme beim Lernen: <ul> <li>Größe des Hypothesenraums im Vergleich zur Anzahl der Trainingsdaten.</li> <li>Das Verfahren könnte nur suboptimale Lösungen finden.</li> <li>Das Verfahren könnte die passende Hypothese nicht beinhalten.</li> </ul> </li> <li>Lernproblemtypen: Sei die Menge der Lernbeispiele in \(X \times Y\), mit \(X \times Y =\)… <ul> <li>\(\{Attribut_1, Attribut_2, …\} \times \{True, False\}\): Konzeptlernen</li> <li>\(\mathbb{R}^n \times \{Klasse_1, …, Klasse_n\}\): Klassifikation</li> <li>\(\mathbb{R}^n \times \mathbb{R}\): Regression</li> </ul> </li> <li>Gradientenabstieg, Overfitting</li> <li>Kreuzvalidierung</li> <li>PAC <ul> <li>Folie 35: Was ist eine Instanz der Länge \(n\)?<br /> Eine Hypothese mit \(n\) Literalen.</li> </ul> </li> </ul> <h4 id="boosting">Boosting</h4> <dl> <dt><a href="https://de.wikipedia.org/wiki/Boosting"><dfn>Boosting</dfn></a></dt> <dd>Kombiniere mehrere schwache Modelle um ein gutes zu bekommen, indem Trainingsbeispiele unterschiedlich gewichtet werden.</dd> <dt><a href="https://en.wikipedia.org/wiki/Bootstrap_aggregating"><dfn>Bagging</dfn></a> (<dfn>Bootstrap aggregating</dfn>)</dt> <dd>Kombiniere mehrere schwache Modelle um ein gutes zu bekommen. Dabei bekommt jedes schwache Modell nur eine Teilmenge aller Trainingsdaten.</dd> <dt><dfn>AdaBoost</dfn> (<dfn>Adaptive Boosting</dfn>; see <a href="https://www.youtube.com/watch?v=ix6IvwbVpw0">YouTube</a>)</dt> <dd>Learn a classifier for data. Get examples where the classifier got it wrong. Train new classifier on the wrong ones.</dd> </dl> <ul> <li>Folie 22: <ul> <li>Wofür steht \(i\) und welchen Wertebereich hat \(i\)?<br /> → \(i\) ist eine Zählvariable, welche die Trainingsdaten durchnummeriert.</li> <li>Stellt \(W_k(i)\) die Wahrscheinlichkeit dar, dass Beispiel \(i\) im \(k\)-ten Durchlauf für das Training verwendet wird?<br /> → Nein. \(W_k(i)\) ist das Gewicht des \(i\)-ten Trainingsbeispiels für den \(k\)-ten klassifikator. Siehe Folie 24 und folgende für ein Beispiel.</li> </ul> </li> </ul> <p>Siehe auch:</p> <ul> <li>Alexander Ihler: <a href="https://www.youtube.com/watch?v=ix6IvwbVpw0">AdaBoost</a>.</li> </ul> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/ml-ensemble-learning.png"><img src="//martin-thoma.com/captions/ml-ensemble-learning.png" alt="Ensemble Learning Techniques: Boosting, Bagging, Random Subspaces, Pasting, Random Patches" width="500" height="478" class="" /></a><p class="wp-caption-text">Ensemble Learning Techniques: Boosting, Bagging, Random Subspaces, Pasting, Random Patches</p></div> <h4 id="vc-dimension">VC-Dimension</h4> <dl> <dt><dfn>VC-Dimension</dfn>, siehe <a href="https://youtu.be/puDzy2XmR5c">YouTube</a> und [<a href="#ref-mit97" name="ref-mit97-anchor">Mit97</a>]</dt> <dd>Sei \(H^\alpha = \{h_\alpha : \alpha \in A\}\) der Hypothesenraum. Die VC-Dimension \(VC(h_\alpha)\) von \(H^\alpha\) ist gleich der maximalen Anzahl von beliebig platzierten Datenpunkten, die von \(H^\alpha\) separiert werden können.</dd> </dl> <ul> <li>Folie 44: \(\eta \in [0, 1]\) ist ein Parameter, der beliebig gewählt werden kann. Siehe Info-Box <a href="#fehlerabschaetzung">Abschätzung des realen Fehlers</a>.</li> </ul> <h3 id="neuronale-netze">Neuronale Netze</h3> <p>Slide name: <code>MLI_05_Neuronale_Netze_slides1.pdf</code></p> <ul> <li>Einsatzfelder: <ul> <li>Klassifiktion: Spracherkennung, Schrifterkennung</li> <li>Funktionsapproximation</li> <li>Mustervervollständigung: Kodierung, Bilderkennung (NODO: Warum zählt das nicht zu Klassifikation?)</li> </ul> </li> <li>Perzeptron von Rosenblatt (1960) <ul> <li>Auswertung: Input-Vektor und Bias mit Gewichten multiplizieren, addieren und Aktivierungsfunktion anwenden.</li> <li>Training: Zufällige Initialisierung des Gewichtsvektors, addieren von fehlklassifizierten Vektoren auf Gewichtsvektor.</li> </ul> </li> <li>Gradientenabstieg</li> <li>Software: <ul> <li><a href="http://lasagne.readthedocs.org/en/latest/index.html">Lasagne</a>: Python, hat eine exzellente Dokumentation, die auch größtenteils auf explizit auf Literatur verweist und die Formeln hinter den Funktionen direkt angibt.</li> <li><a href="https://martin-thoma.com/tensor-flow-quick/">Google TensorFlow</a></li> </ul> </li> </ul> <dl> <dt><dfn>Cascade Correlation</dfn></dt> <dd>Cascade Correlation ist ein konstruktiver Algorithmus zum erzeugen von Feed-Forward Neuronalen Netzen. Diese haben eine andere Architektur als typische multilayer Perceptrons. Bei Netzen, welche durch Cascade Correlation aufgebaut werden, ist jede Hidden Unit mit den Input-Neuronen verbunden, mit den Output-Neuronen und mit allen Hidden Units in der Schicht zuvor.</dd> <dt><a href="https://en.wikipedia.org/wiki/Rprop"><abbr title="Resilient Propagation"><dfn>RPROP</dfn></abbr></a> (siehe <a href="https://www.youtube.com/watch?v=Cy2g9_hR-5Y">YouTube</a> - 15:00min)</dt> <dd><i>Rprop</i> ist eine Gewichtsupdate-Regel für neuronale Netze. Sie betrachtet nur das Vorzeichen des Gradienten, jedoch nicht den Betrag. Jedes Gewicht wird unabhängig von den anderen behandelt. Der Algorithmus hat Konstanten \(\eta^- \in \mathbb{R}_{\le 1}\) sowie \(\eta^+ \in \mathbb{R}_{\ge 1}\). Für jedes Gewicht ist außerdem \(\eta=1\) zu Beginn. Bei jedem Gewichtsupdate wird überprüft, ob sich das Vorzeichen des Gradienten für dieses Gewicht geändert hat. Falls ja, wird das Gewicht um \(\eta \cdot \eta^+\) bzw \(\eta \cdot \eta^-\) geändert. Außerdem kann eine minimale bzw. eine Maximale Änderung gesetzt werden. </dd> <dt><a href="https://en.wikipedia.org/wiki/Delta_rule"><dfn>Delta-Regel</dfn></a>, siehe <a href="http://www.neuronalesnetz.de/delta.html">neuronalesnetz.de</a></dt> <dd>Die Delta-Regel ist ein Lernalgorithmus für neuronale Netze mit nur einer Schicht. Sie ist ein Spezialfall des algemeineren Backpropagation-Algorithmus und lautet wie folgt: \[\Delta w_{ji} = \alpha (t_j - y_j) \varphi'(h_j) x_i\] wobei <ul> <li>\(\Delta w_{ji} \in \mathbb{R}\) die Änderung des Gewichts von Input \(i\) zum Neuron \(j\),</li> <li>\(\alpha \in [0, 1]\) die Lernrate (typischerweise \(\alpha \approx 0.1\)),</li> <li>\(t_j \in \mathbb{R}\) der Zielwert des Neurons \(j\),</li> <li>\(y_j \in \mathbb{R}\) die tatsächliche Ausgabe,</li> <li>\(\varphi'\) die Ableitung der Aktivierungsfunktion des Neurons,</li> <li>\(h_j \in \mathbb{R}\) die gewichtete Summe der Eingaben des Neurons und</li> <li>\(x_i \in \mathbb{R}\) der \(i\)-te Input</li> </ul> ist. </dd> <dt><dfn>Gradient-Descent Algorithmus</dfn></dt> <dd>Der Gradient-Descent Algorithmus ist ein Optimierungsalgorithmus für differenzierbare Funktionen. Er startet an einer zufälligen Stelle \(x_0\). Dann wird folgender Schritt mehrfach ausgeführt: \[x_0 \gets x_0 - \alpha \cdot \text(grad) f (x_0)\] wobei \(\alpha \in (0, 1]\) die Lernrate ist und \(f\) die zu optimierende Funktion. Dabei könnte \(\alpha\) mit der Zeit auch kleiner gemacht werden. </dd> <dt><dfn>Backpropagation</dfn> (siehe <a href="http://neuralnetworksanddeeplearning.com/chap2.html">neuralnetworksanddeeplearning.com</a>)</dt> <dd>Der Backpropagation-Algorithmus ist eine Variante des Gradient-Descent Algorithmus, welche für <abbr title="multilayer Perceptrons">MLPs</abbr> angepasst wurde. Sie besteht aus drei Schritten: <ul> <li><b>Forward-Pass</b>: Lege die Input-Features an das Netz an und erhalte den Output</li> <li><b>Fehlerberechnung</b>: Mache das für alle Daten</li> <li><b>Backward-Pass</b>: Passe die Gewichte </li> </ul> Im Grunde ist Backpropagation nur eine Geschwindigkeitsoptimierte Variante des Gradient-Descent Algorithmus, da die Gradienten im Backpropagation-Algorithmus auf geschickte Weise berechnet werden.</dd> <dt><a href="https://de.wikipedia.org/wiki/Radiale_Basisfunktion"><dfn>Radiale Basisfunktion</dfn></a> (<dfn>Radial Basis Function</dfn>, <dfn>RBF</dfn>)</dt> <dd>Eine <i>radiale Basisfunktion</i> ist eine Funktion \(f: D \rightarrow \mathbb{R}\), für die \(f(x) = f(\|x\|)\) gilt bzw. allgemeiner, für die ein \(c \in D\) existiert, sodass \(f(x, c) = f(\|x - c\|)\) gilt. Der Wert der Funktion hängt also nur von der Distanz zum Ursprung bzw. allgemeiner zu einem Punkt \(c \in D\) ab. Ein typisches Beispiel sind gaußsche RBFs: \(f(x) = e^{-(a (x - c)^2)}\), wobei \(a, c\) Konstanten sind.</dd> <dt><a href="https://en.wikipedia.org/wiki/Radial_basis_function_network"><dfn>Radial-Basis Funktion Netz</dfn></a> (<dfn>RBF-Netz</dfn>)</dt> <dd>Ein <i>Radial-Basis Funktion Netz</i> ist eine neuronales Netz, welches als Aktivierungsfunktionen RBFs verwendet. Dabei gibt es dann für jedes Neuron im Grunde zwei Parameter: Der Radius und das Zentrum (vgl. Folie&nbsp;39 für die Gewichtsanpassung). </dd> <dt><a name="dda-algorithm"></a><dfn>Dynamic Decay Adjustment</dfn> (<dfn>DDA</dfn>)</dt> <dd>DDA ist ein konstruktiver Lernalgorithmus für RBF-Netze welcher in [<a href="#ref-ber95" name="ref-ber95-anchor">Ber95</a>] vorgestellt wird. Bei den Netzwerken, die DDA annimmt, gibt es sog. <i>Prototypen</i>. Das scheinen einfach Neuronen mit RBF-Aktivierungsfunktionen zu sein, welche für eine Klasse stehen. Zwei Schwellwerte, \(\theta^+\) und \(\theta^-\), werden eingeführt. Der Schwellwert \(\theta^+\) muss beim Training eines Beispiels der Klasse \(y_1\) von einem Neuron der Klasse \(y_1\) überschritten werden. Falls das nicht der Fall ist, wird ein neues Neuron hinzugefügt.<br /> Der Schwellwert \(\theta^-\) ist eine obere Grenze für die Aktivierung von Neuronen, die zu anderen Klassen gehören. Ist eine Aktivierung höher, wird der Radius des zugehörigen Neurons verringert.<br /> \(\theta^+ = 0.4\) und \(\theta^- = 0.2\) sind sinnvolle Werte. <br /> Laut einem Prüfungsprotokoll lernt DDA nach Vapnik korrekt.<br /> <br /> Siehe auch: <a href="http://www.ra.cs.uni-tuebingen.de/SNNS/UserManual/node193.html">The Dynamic Decay Adjustment Algorithm</a></dd> </dl> <h4 id="siehe-auch-1">Siehe auch</h4> <ul> <li><a href="//martin-thoma.com/neuronale-netze-vorlesung/">Neuronale Netze - Vorlesung</a></li> <li><a href="http://datascience.stackexchange.com/q/9672/8820">How exactly does adding a new unit work in Cascade Correlation?</a></li> <li><a href="http://datascience.stackexchange.com/q/9869/8820">What are prototypes in RBF networks?</a></li> </ul> <h3 id="instanzbasiertes-lernen">Instanzbasiertes Lernen</h3> <p>Slide name: <code>MLI_06_InstanzbasiertesLernen_slides1.pdf</code></p> <dl> <dt><dfn>Instanzenbasiertes Lernen</dfn> bzw. <dfn>Lazy Learning</dfn></dt> <dd><i>Instanzenbasiertes Lernen</i> ist ein Lernverfahren, welches einfach nur die Beispiele abspeichert, also faul (engl. lazy) ist. Soll der Lerner neue Daten klassifizieren, so wird die Klasse des ähnlichsten Datensatzes gewählt.</dd> <dt><dfn>Case-based Reasoning</dfn> bzw. kurz <dfn>CBR</dfn></dt> <dd><i>CBR</i> ist ein allgemeines, abstraktes Framework und kein direkt anwendbarer Algorithmus. Die Idee ist, dass nach ähnlichen, bekannten Fällen gesucht wird, auf die der aktuelle Fall übertragen werden kann.</dd> <dt><dfn>Fall</dfn> im Kontext des CBR</dt> <dd>Ein Fall ist eine Abstraktion eines Ereignisses, die in Zeit und Raum begrenzt ist. Ein Fall enthält eine Problembeschreibung, eine Lösung und ein Ergebnis. Zusätzlich kann ein Fall eine Erklärung enthalten warum das Ergebnis auftrat, Informationen über die Lösungsmethode, Verweise auf andere Fälle oder Güteinformationen enthalten.</dd> </dl> <ul> <li> <p>Beispiel für Lazy Learning: <abbr title="k Nearest Neighbors">(k)-NN</abbr>, <abbr title="Case-based Reasoning">CBR</abbr></p> </li> <li> <p>NODO: Folie 3: „Fleißige“ Lernalgorithmen mit dem gleichen Hypothesenraum sind eingeschränkter - was ist damit gemeint? Was sind fleißige Lernalgorithmen? Lernalgorithmen, welche den meisten Rechenaufwand beim Lernen investieren, wo aber das auswerten vergleichsweise billig ist?</p> </li> </ul> <h3 id="a-namesvma-svm"><a name="svm"></a> SVM</h3> <p>Slide name: <code>MLI_07_SVM_slides1.pdf</code></p> <p>Eine Erklärung von <abbr title="Support Vector Machines">SVMs</abbr> findet sich im Artikel <a href="//martin-thoma.com/svm-with-sklearn/">Using SVMs with sklearn</a>.</p> <ul> <li>SVMs sind laut Vapnik die Lernmaschine mit der kleinsten möglichen VC- Dimension, falls die Klassen linear trennbar sind.</li> <li>Primäres Optimierungsproblem: Finde einen Sattelpunkt der Funktion<br /> \(L_P = L(\vec{w}, b, \vec{\alpha}) = \frac{1}{2}|\vec{w}|^2 - \sum_{i=1}^N \alpha_i (y_i(\vec{w}\vec{x_i}+b)-1)\) wobei \(\alpha_1, \dots, \alpha_N \geq 0\) Lagrange-Multiplikatoren sind</li> <li>Soft Margin Hyperebene</li> <li>Der Parameter (C) dient der Regularisierung. Ist (C) groß gibt es wenige Missklassifikationen in der Trainingsdatenmenge. Ist (C) klein, werden die Margins größer.</li> <li>Nichtlineare Kernelmethoden</li> <li>Kernel-Trick</li> </ul> <div class="alert alert-info"><h4><a name="fehlerabschaetzung"></a>Abschätzung des realen Fehlers</h4> Der reale Fehler kann durch den empirischen Fehler und die VC-Dimension wie folgt abgeschätzt werden: Mit Wahrscheinlichkeit \(P(1-\eta)\) gilt: \[E(h_\alpha) \leq E_{emp}(h_\alpha) + \sqrt{\frac{VC(h_\alpha)}{N} \cdot (\log(2 N / VC(h_\alpha)) + 1) - \frac{\log(\eta / 4)}{N}}\] wobei gilt: <ul> <li>\(E(h_\alpha)\) ist der reale Fehler der mit der Hypothese \(h_\alpha\) gemacht wird</li> <li>\(E_{emp}(h_\alpha)\) ist der empirische Fehler der mit der Hypothese \(h_\alpha\) gemacht wird</li> <li>\(VC(h_\alpha)\) ist die VC-Dimension der Lernmaschine</li> <li>\(N\) ist die Anzahl der Lernbeispiele</li> <li>\(0 \leq \eta \leq 1\)</li> </ul> Dieser Term wird in der <i>Structural Risc Minimization</i> minimiert. </div> <h3 id="a-namedecision-treesa-entscheidungsbume"><a name="decision-trees"></a> Entscheidungsbäume</h3> <p>Slide name: <code>MLI_08_Entscheidungsbaeume_slides1.pdf</code></p> <dl> <dt><dfn>Entscheidungsbaum</dfn> (<dfn>Decision Tree</dfn>)</dt> <dd>Ein Entscheidungsbaum ist ein Klassifikator in Baumstruktur. Die inneren Knoten des Entscheidungsbaumes sind Attributtests, die Blätter sind Klassen.<br /> <br /> Typischerweise wird ein Entscheidungsbaum aufgebaut, indem das jeweilige Attribut mit dem höchsten Information Gain als nächster Knoten hinzugefügt wird. Siehe <a href="https://en.wikipedia.org/wiki/Information_gain_in_decision_trees">Information gain in decision trees</a> für weitere Informationen.</dd> <dt><a href="https://de.wikipedia.org/wiki/ID3"><dfn>ID3</dfn></a> (siehe <a href="(https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/ID3">pseudocode</a>)</dt> <dd>ID3 ist ein Top-Bottom Verfahren zum Aufbau eines Entscheidungsbaumes.</dd> <dt><a href="https://de.wikipedia.org/wiki/C4.5"><dfn>C4.5</dfn></a> (siehe <a href="(https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/ID3">pseudocode</a>)</dt> <dd>ID3 ist ein Top-Bottom Verfahren zum Aufbau eines Entscheidungsbaumes, welches auf ID3 basiert.</dd> <dt><dfn>Random Forest</dfn>, Quelle: <a href="https://de.wikipedia.org/wiki/Random_Forest">Wikipedia</a></dt> <dd>Ein Random Forest ist ein Klassifikationsverfahren, welches aus mehreren verschiedenen, unkorrelierten Entscheidungsbäumen besteht. Alle Entscheidungsbäume sind unter einer bestimmten Art von Randomisierung während des Lernprozesses gewachsen. Für eine Klassifikation darf jeder Baum in diesem Wald eine Entscheidung treffen und die Klasse mit den meisten Stimmen entscheidet die endgültige Klassifikation.</dd> </dl> <ul> <li>Der Algorithmus ID5R dienen dem Aufbau eines Entscheidungsbaumes.</li> <li>C4.5 unterstützt - im Gegensatz zu ID3 - kontinuierliche Attributwerte. Außerdem kann C4.5 mit fehlenden Attributwerten umgehen.</li> <li>Mögliches Qualtitätsmaß ist Entropie:<br /> \(Entropie(S) = - p_\oplus \log_2 p_\oplus - p_\ominus \log_2 p_\ominus\) wobei \(\oplus\) die positiven Beispiele und \(\ominus\) die negativen Beispiele bezeichnet.</li> <li>Folie 41: Wo ist der Vorteil von ID5R im Vergleich zu ID3, wenn das Ergebnis äquivalent ist?<br /> → ID5R kann inkrementell verwendet werden. Es ist bei ID5R - im Gegensatz zu ID3 - also nicht nötig bei neuen Trainingsdaten neu zu trainieren.</li> <li>Random Forest: Erstelle mehrere Entscheidungsbäume mit einer zufälligen Wahl an Attributen. Jeder Baum stimmt für eine Klasse und die Klasse, für die die meisten Stimmen, wird gewählt.</li> </ul> <h3 id="bayes-lernen">Bayes Lernen</h3> <p>Slide name: <code>MLI_09_BayesLernen_slides1.pdf</code></p> <p>Siehe auch:</p> <ul> <li><a href="https://martin-thoma.com/machine-learning-2-course/#dynamic-bayes-networks">Dynamische Bayesssche Netze</a> in ML2</li> </ul> <dl> <dt><dfn>Satz von Bayes</dfn></dt> <dd>Seien \(A, B\) Ereignisse, \(P(B) &gt; 0\). Dann gilt: \(P(A|B) = \frac{P(B|A) \cdot P(A)}{P(B)}\)<br /> Dabei wird \(P(A)\) a priori Wahrscheinlichkeit, \(P(B|A)\) likelihood, und \(P(A|B)\) a posteriori Wahrscheinlichkeit genannt.</dd> <dt><dfn>Naiver Bayes-Klassifikator</dfn></dt> <dd>Ein Klassifizierer heißt naiver Bayes-Klassifikator, wenn er den Satz von Bayes unter der naiven Annahme der Unabhängigkeit der Features benutzt.</dd> <dt><dfn>Produktregel</dfn></dt> <dd>\(P(A \land B) = P(A|B) \cdot P(B) = P(B|A) \cdot P(A)\)</dd> <dt><dfn>Summenregel</dfn></dt> <dd>\(P(A \lor B) = P(A) + P(B) - P(A \land P)\)</dd> <dt><dfn>Theorem der totalen Wahrscheinlichkeit</dfn></dt> <dd>Es seien \(A_1, \dots, A_n\) Ereignisse mit \(i \neq j \Rightarrow A_i \cap A_j = \emptyset \;\;\;\forall i, j \in 1, \dots, n\) und \(\sum_{i=1}^n A_i = 1\). Dann gilt:<br /> \(P(B) = \sum_{i=1}^n P(B|A_i) P(A_i)\)</dd> <dt><dfn>Maximum A Posteriori Hypothese</dfn> (MAP-Hypothese)</dt> <dd>Sei \(H\) der Raum aller Hypothesen und \(D\) die Menge der beobachteten Daten. Dann heißt<br /> \(h_{MAP} = \text{arg max}_{h \in H} P(h|D) \cdot P(h)\)<br /> die Menge der Maximum A Posteriori Hypothesen.</dd> <dt><dfn>Maximum Likelihood Hypothese</dfn> (ML-Hypothese)</dt> <dd>Sei \(H\) der Raum aller Hypothesen und \(D\) die Menge der beobachteten Daten. Dann heißt<br /> \(h_{ML} = \text{arg max}_{h \in H} P(h|D)\)<br /> die Menge der Maximum Likelihood Hypothesen.</dd> <dt><dfn>Normalverteilung</dfn></dt> <dd>Eine stetige Zufallsvariable \(X\) mit der Wahrscheinlichkeitsdichte \(f\colon\mathbb{R}\to\mathbb{R}\), gegeben durch<br /> \(f(x) = \frac {1}{\sigma\sqrt{2\pi}} e^{-\frac {1}{2} \left(\frac{x-\mu}{\sigma}\right)^2}\)<br /> heißt \(\mathcal N\left(\mu, \sigma^2\right)\)-verteilt, normalverteilt mit den Erwartungswert \(\mu\) und Varianz \(\sigma^2\).</dd> <dt><a href="https://de.wikipedia.org/wiki/Minimum_Description_Length"><dfn>Prinzip der minimalen Beschreibungslänge</dfn></a></dt> <dd>Das Prinzip der minimalen Beschreibungslänge ist eine formale Beschreibung von Ockhams Rasiermesser. Nach diesem Prinzip werden Hypothesen bevorzugt, die zur besten Kompression gegebener Daten führen. </dd> <dt><a href="https://de.wikipedia.org/wiki/Gibbs-Sampling"><dfn>Gibbs-Algorithmus</dfn></a> (<a href="http://stats.stackexchange.com/a/10216/25741">stats.stackexchange</a>)</dt> <dd>Der Algorithmus von Gibbs ist eine Methode um Stichproben von bedingten Verteilungen zu erzeugen. </dd> <dt><a href="https://de.wikipedia.org/wiki/Bedingte_Unabh%C3%A4ngigkeit"><dfn>Bedingte Unabhängigkeit</dfn></a></dt> <dd>Seien \(X, Y, Z\) Zufallsvariablen. Dann heißt \(X\) bedingt unabhängig von \(Y\) gegeben \(Z\), wenn \[P(X|Y,Z) = P(X|Z)\] gilt. </dd> <dt><a href="https://en.wikipedia.org/wiki/Additive_smoothing"><dfn>Add \(k\) smoothing</dfn></a></dt> <dd>Unter Add-\(k\)-smoothing versteht man eine Technik, durch die sichergestellt wird, dass die geschätzte Wahrscheinlichkeit für kein Ereignis gleich null ist. Wenn man \(d \in \mathbb{N}\) mögliche Ergebnisse eines Experiments hat, \(N \in \mathbb{N}\) experimente durchgeführt werden, dann schätzt man die Wahrscheinlichkeit von dem Ergebnis \(i\) mit \[\hat{\theta_i} = \frac{x_i + k}{N+ kd}, \] wobei \(x_i\) die Anzahl der Beobachtungen von \(i\) ist und \(k \geq 0\) der Glättungsparameter ist. </dd> <dt><a href="https://de.wikipedia.org/wiki/Bayessches_Netz"><dfn>Bayessches Netz</dfn></a> (Quelle: [<a href="#ref-dar09" name="ref-dar09-anchor">Dar09</a>])</dt> <dd>Ein bayessches Netz ist ein Tupel \((G, \Theta)\) mit: <ul> <li>\(G = (\mathbf{X}, E)\) ist ein <abbr title="Directed Acyclical Graph">DAG</abbr> der <b>Struktur</b> des Bayesschen Netzwerks genant wird. Dabei ist \(\mathbf{X} = \{X_1, X_2, \dots, X_n\}\) die Menge der Knoten. Jeder Knoten entspricht einer Zufallsvariablen. Existiert eine gerichtete Kante \((X_i, X_j) \in E\), so existiert eine direkte Abhängigkeit zwischen \(X_i\) und \(X_j\).</li> <li>\(Theta\) ist die Menge der bedingten Wahrscheinlichkeitsverteilungen und heißt <b>Parametrisierung</b> des bayesschen Netzwerks. Es existiert für jedes \(X_i\) genau eine Verteilung in \(\Theta\), welche in Abhängigkeit der Elternknoten beschrieben wird.</li> </ul> In einem bayesschem Netz berechnet sich die gemeinsame Verteilung wie folgt: \[P(X_1, \dots, X_N) = \prod_{i=1}^N P(X_i | \text{Eltern}(X_i))\] Die Modelierung von Bayesschen Netzen erfolgt meist durch den Menschen mit Expertenwissen. Alternativ kann die Struktur durch <abbr title="Markov Chain Monte Carlo">MCMC</abbr> bestimmt werden. Sobald die Struktur gegeben ist wird die Menge der Verteilungen \(\Theta\) durch den Expectation Maximization Algorithmus bestimmt. </dd> </dl> <p>Fragen:</p> <ul> <li>Folie 23: Warum ist \(h_{MAP(x)}\) nicht die wahrscheinlichste Klassifikation?</li> <li>Folie 24: Was ist \(V\)?</li> <li><a href="http://datascience.stackexchange.com/q/9818/8820">Is there any domain where Bayesian Networks outperform neural networks?</a></li> </ul> <h3 id="a-namehmma-hmm"><a name="hmm"></a> HMM</h3> <p>Slide name: <code>MLI_10_HMM_slides1.pdf</code></p> <dl> <dt><dfn>Markov-Bedingung</dfn> (Beschränkter Horizont)</dt> <dd>\(P(q_{t+1}=S_{t+1}|q_t = S_t, q_{t-1} = S_{t-1}, \dots) = P(q_{t+1}=S_{t+1}|q_t = S_t)\)</dd> <dt><dfn>Hidden Markov Modell</dfn> (<dfn>HMM</dfn>)</dt> <dd>Eine HMM ist ein Tupel \(\lambda = (S, V, A, B, \Pi)\): <ul> <li>\(S = \{S_1, \dots, S_n\}\): Menge der Zustände</li> <li>\(V = \{v_1, \dots, v_m\}\): Menge der Ausgabezeichen</li> <li>\(A \in [0,1]^{n \times n}\) = (a_{ij}): Übergangsmatrix, die die Wahrscheinlichkeit von Zustand \(i\) in Zustand \(j\) zu kommen beinhaltet</li> <li>\(B = (b_{ik})\) die Emissionswahrscheinlichkeit \(v_k\) im Zustand \(S_i\) zu beobachten</li> <li>\(\Pi = (\pi_i) = P(q_1 = i)\): Die Startverteilung, wobei \(q_t\) den Zustand zum Zeitpunkt \(t\) bezeichnet</li> </ul></dd> <dt><a href="https://de.wikipedia.org/wiki/Forward-Algorithmus"><dfn>Vorwärts-Algorithmus</dfn></a></dt> <dd>Der Vorwärts-Algorithmus löst das Evaluierungsproblem. Er benutzt dazu dynamische Programmierung: Die Variablen \(\alpha_t(i) = P(o_1 o_2 \dots o_t; q_t = s_i | \lambda)\) gibt die Wahrscheinlichkeit an zum Zeitpunkt \(t \in 1 \leq t \leq T\) im Zustand \(s_i \in S\) zu sein und die Sequenz \(o_1 o_2 \dots o_t\) beobachtet zu haben. Diese werden rekursiv berechnet. Dabei beginnt man mit Zeitpunkt \(t=1\), berechnet die Wahrscheinlichkeit \(o_1\) beobachtet zu haben für jeden Zustand. <br /> Die Wahrscheinlichkeit der beobachteten Sequenz, gegeben die HMM \(\lambda\), ist dann einfach die Summe der \(\alpha_i\) des letzten Zeitschritts.</dd> <dt><a href="https://de.wikipedia.org/wiki/Backward-Algorithmus"><dfn>Rückwärts-Algorithmus</dfn></a></dt> <dd>Der Rückwärts-Algorithmus löst das Dekodierungsproblem. Er benutzt dazu dynamische Programmierung: Die Variablen \(\beta_t(i) = P(o_{t+1} o_{t+2} \dots o_{T}|q_t = s_i, \lambda)\) geben die Wahrscheinlichkeit an, dass die Sequenz \(o_{t+1} o_{t+2} \dots o_{T}\) beobachtet werden wird, gegeben das HMM&nbsp;\(\lambda\) und den Startzustand&nbsp;\(s_i\).</dd> <dt><dfn>Forward-Backward Algorithm</dfn></dt> <dd>Der Forward-Backward Algorithmus berechnet für jeden Zeitpunkt die Wahrscheinlichkeitsverteilung der Zustände. Dafür glättet er die Werte des Vorwärts- und des Rückwärts-Algorithmus: \[\gamma_t(i) = \frac{\alpha_t(i) \beta_t(i)}{P(O|\lambda)}\] Er findet jedoch nicht die wahrscheinlichste Zustandssequenz. </dd> <dt><a href="https://de.wikipedia.org/wiki/Viterbi-Algorithmus"><dfn>Viterbi-Algorithmus</dfn></a></dt> <dd>Löst P2: <br /> Siehe <a href="../apply-viterbi-algorithm/">How to apply the Viterbi algorithm</a></dd> <dt><a href="https://de.wikipedia.org/wiki/Baum-Welch-Algorithmus"><dfn>Baum-Welch-Algorithmus</dfn></a></dt> <dd>Löst P3: Gegeben sei eine Trainingssequenz \(O_{\text{train}}\) und ein Modell \[\lambda = \{S, V, A, B, \Pi\}\] Gesucht ist ein Modell \[\bar \lambda = \text{arg max}_{\bar \lambda = \{S, V, \bar A, \bar B, \bar Pi\}} P(O_{\text{train}}|\lambda)\] Der Baum-Welch-Algorithmus geht wie folgt vor: <ol> <li>Bestimme \(P(O_{\text{train}} | \lambda)\)</li> <li>Schätze ein besseres Modell \(\bar \lambda\): TODO - Genauer! (Folie 31 - 36)</li> </ol> Iteriere diese Schritte so lange, bis ein lokales Maximum gefunden wurde. </dd> <dt><dfn>Ergodisches Modell</dfn></dt> <dd>Unter dem <i>ergodischen Modell</i> versteht man im Kontext von <abbr title="Hidden Markov Models">HMMs</abbr> die vollverbundene Topologie inclusive Schleifen.</dd> <dt><dfn>Bakis-Modell</dfn> (<dfn>Links-nach-Rechts-Modell</dfn>)</dt> <dd>Unter dem <i>Bakis-Modell</i> versteht man im Kontext von <abbr title="Hidden Markov Models">HMMs</abbr> eine Links-nach-Rechts Topologie, bei der maximal ein Zustand übersprungen werden kann. Das bedeutet, es gibt eine Ordnung über den Zuständen. Von einem Zustand \(i\) kommt man in die Zustände \(i, i+1, i+2\).</dd> </dl> <p>Die drei Probleme von HMMs sind</p> <ul> <li><strong>P1 - Evaluierungsproblem</strong>: Wie wahrscheinlich ist eine Sequenz \(\bf{o} = o_1 o_2 \dots o_T\) gegeben ein HMM \(\lambda\), also \(P(\bf{o}|\lambda)\).</li> <li><strong>P2 - Dekodierungsproblem</strong>: Finden der wahrscheinlichsten Zustandssequenz <span>\(s_1, \dots, s_T\)</span>, gegeben eine Sequenz von Beobachtungen \(\bf{o} = o_1 o_2 \dots o_T\).</li> <li><strong>P3 - Lernproblem</strong>: Optimieren der Modellparameter</li> </ul> <p>Anwendungen:</p> <ul> <li>Gestenerkennung</li> <li>Phonem-Erkennung</li> </ul> <h3 id="markov-logik-netze">Markov Logik Netze</h3> <p>Slides: <code>MLI_11-MLN_slides1</code></p> <p>Markov Logik Netze sind Sammlungen von Tupeln aus Gewichten \(w_i\) und prädikatenlogischen Formeln. Die Idee hinter Markov Logik Netzen ist ein aufweichen der harten Bedingungen der Prädikatenlogik. Eine prädikatenlogische Formel ist entweder wahr oder falsch. Eine Formel in MLNs kann auch “meistens” erfüllt sein. Das wird durch das Gewicht repräsentiert.</p> <dl> <dt><a href="https://de.wikipedia.org/wiki/Markov_Logik_Netze"><dfn>Markov Logik Netze</dfn></a> (<dfn>MLN</dfn>)</dt> <dd>Ein Markov Logik Netz ist ein Menge aus Tupeln \(L = (F_i, w_i)\), wobei \(F_i\) eine Formel der Prädikatenlogik erster Ordnung und \(w_i \in \mathbb{R}\) ein Gewicht ist. Ein MLN ist eine Schablone für ein MRF.</dd> <dt><a name="mrf-definition"></a><dfn>Markov Random Field</dfn> (<dfn>Markov Netzwerk</dfn>, <dfn>MRF</dfn>)</dt> <dd>Ein MRF ist ein ungerichtetes Probabilistisches Grafisches Modell.<br /> MRFs sind zur Modellierung von Korrelation geeignet.</dd> <dt><a name="mln-jpd"></a><dfn>Verbundwahrscheinlichkeit in MLNs</dfn></dt> <dd>\(P(x) = \frac{1}{Z} \exp(\sum_{i} w_i f_i(x))\) wobei \(f_i\) das \(i\)-te Feature und \(w_i\) ein Gewicht ist. Beispielsweise könnte \[f_i(x) = f_i(\text{smoking}, \text{cancer}) = \begin{cases}1 &amp;\text{if } \neg \text{smoking} \lor \text{cancer}\\ 0 &amp;\text{otherwise}\end{cases}\] gelten.</dd> <dt><a name="mln-inference"></a><dfn>Inferenz in MLNs</dfn></dt> <dd><abbr title="Maximum a posteriori">MAP</abbr>: \[\begin{align}\text{arg max}_y P(y | x) &amp;= \frac{1}{Z} \exp(\sum_{i} w_i n_i(x, y))\\ &amp;= \sum_{i} w_i n_i(x, y) \end{align}\]</dd> </dl> <p>Siehe auch:</p> <ul> <li>Matthew Richardson, Pedro Domingos: <a href="http://link.springer.com/article/10.1007/s10994-006-5833-1">Markov logic networks</a></li> <li>Pedro Domingos, Matthew Richardson: <a href="http://homes.cs.washington.edu/~pedrod/papers/srl04.pdf">Markov Logic: A Unifying Framework for Statistical Relational Learning</a>, 2007.</li> <li>Coursera: <a href="https://www.coursera.org/course/pgm">Probabilistic Graphical Models</a></li> <li>Pedro Domingos: <a href="https://www.youtube.com/watch?v=bW5DzNZgGxY">Unifying Logical and Statistical AI</a>, September 2009.</li> <li>Software: <a href="https://alchemy.cs.washington.edu/">Alchemy</a></li> <li>YouTube: <a href="https://www.youtube.com/watch?v=BLAoNJvQZQ4">11 4 M4 Markov Logic Formalism 11 39</a></li> </ul> <h3 id="evolutionre-algorithmen">Evolutionäre Algorithmen</h3> <p>Slides: <code>MLI_12_EvolutionaereAlgorithmen_slides1.pdf</code></p> <p>Siehe auch:</p> <ul> <li>[<a href="#ref-mit97" name="ref-mit97-anchor">Mit97</a>]</li> <li><a href="http://deap.readthedocs.org/en/master/index.html">DEAP</a> wenn du es ausprobieren willst.</li> <li><a href="http://stackoverflow.com/q/7787232/562769">Difference between genetic algorithms and evolution strategies?</a></li> </ul> <dl> <dt><dfn>Individuum</dfn></dt> <dd>Eine mögliche Hypothese</dd> <dt><dfn>Population</dfn> (<dfn>Generation</dfn>)</dt> <dd>Hypothesenmenge</dd> <dt><dfn>Erzeugung von Nachkommen</dfn></dt> <dd>Generierung neuer Hypothesen durch Rekombination und Mutation</dd> <dt><dfn>Fitness-Funktion</dfn></dt> <dd>Die Fitness-Funktion ist das zu optimierende Kriterium. Sie beschreibt die Güte einer Hypothese.</dd> <dt><dfn>Selektion</dfn></dt> <dd>Auswahl der Hypothesen, welche die beste Problemlösung erzeugen.</dd> <dt><dfn>Evolutionäre Strategien</dfn></dt> <dd>Das Wissen wird durch reele Zahlen und Vektoren repräsentiert.</dd> <dt><dfn>Genetische Programmierung</dfn></dt> <dd>Das Wissen wird duch baumartige Strukturen repräsentiert.</dd> <dt><dfn>Mutation</dfn></dt> <dd>Unter <i>Mutation</i> versteht man die zufällige Änderung einzelner Gene. Beispiele: <ul> <li>Bit-Inversion: Zufällig Gleichverteilt pro Gen / Feste Anzahl, aber zufällige Gene</li> <li>Translation: Verschieben von Teilsequenzen</li> <li>Invertiertes Einfügen</li> <li>Spezielle Mutationsoperatoren sind anwendungsspezifisch</li> </ul> </dd> <dt><dfn>Rekombination</dfn></dt> <dd>Bei der <i>Rekombination</i> werden die Eigenschaften zweier Eltern gemischt. Dies kann Diskret passieren, wenn manche Gene von einem Elternteil übernommen werden und andere vom anderen Elternteil. Alternativ kann die Rekombination auch durch <i>intermediäre Rekombination</i> passieren. Das bedeutet, das ein Gen gemittelt wird.</dd> </dl> <p>Grundalgorithmus:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Fitness-Function f Population p while f(p) ≠ optimal: p_parents ← selection(p) p_children ← generate_children(p_parents) p ← p_parents + p_children fitness ← f(p) p ← selection_kill(p, fitness) </pre></div> </div> </div> <p>Probleme:</p> <ul> <li>Genetischer Drift: Manche Individuen vermehren sich zufällig mehr als andere. Diese sind nicht unbedingt besser für das Problem geeignet.</li> <li>Crowding, Ausreißerproblem: Fitte Individuen dominieren die Population. Das ist ein Problem wegen lokaler Maxima.</li> </ul> <p>Mating:</p> <ul> <li>Inselmodell: Die Evolution läuft weitgehend getrennt. Es passiert nur vereinzelt, dass Individuen der Inseln ausgetauscht werden.</li> <li>Nachbarschaftsmodell: Nachkommen dürfen nur von Individuen erzeugt werden, die in ihrer Nachbarschaft die beste Fitness besitzen</li> <li>Globales Modell: Alle dürfen sich mit allen verbinden.</li> </ul> <p>Evolution:</p> <ul> <li>Lamark’sche Evolution: Die Individuen ändern sich nach der Erzeugung. Sie lernen also. Dabei wird der Genotyp verändert und auch vererbt.</li> <li>Baldwin’sche Evolution: Die Individuen ändern sich nach der Erzeugung, aber der Genotyp bleibt gleich</li> <li>Hybride Verfahren: Es gibt sich verändernde und gleich bleibende Phänotypen.</li> </ul> <p>Anwendungen:</p> <ul> <li>Traveling Salesman</li> <li>Flugplanoptimierung</li> <li>Mischung von Kaffesorten</li> <li>Cybermotten: Motten müssen optimales Muster finden, um sich vor einer Fläche weißen Rauschens zu verbergen.</li> <li>Snakebot (Ivan Tanev) [<a href="#ref-pro06" name="ref-pro06-anchor">Pro06</a>]</li> </ul> <h3 id="deduktives-lernen">Deduktives Lernen</h3> <p>Slides: <code>MLI_13_DeduktivesLernen_slides1.pdf</code></p> <p>Siehe auch: <a href="//martin-thoma.com/formale-systeme/">Formale Systeme</a></p> <dl> <dt><dfn>Modus Ponens</dfn></dt> <dd>\[\frac{A, A \rightarrow B}{B}\]</dd> <dt><dfn>Erklärungsbasiertes Lernen</dfn> (<dfn>EBL</dfn>, <dfn>Explanation Based Learning</dfn> by [<a href="#ref-mit97" name="ref-mit97-anchor">Mit97</a>])</dt> <dd>The key insight behind explanation-based generalization is that it is possible to form a justified generalization of a single positive training example provided the learning system is endowed with some <b>explanatory capabilitie</b>. In particular, the system must be able to explain to itself <b>why the training example is an example of the concept</b> under study. Thus, the generalizer is presumed to possess a definition of the concept under study as well as <b>domain knowledge</b> for constructing the required explanation.</dd> <dt><dfn>Explanation Based Generalization</dfn> (<dfn>EBG</dfn>)</dt> <dd>EBG ist ein Prozess, bei dem implizites Wissen in explizites umgewandelt wird. EBG geht wie folgt vor: <ol> <li>Explain: Finden einer Erklärung, warum das Beispiel die Definition des Zielkonzepts erfüllt. Dies ist einfaches Anwenden des Modus Ponens.</li> <li>Generalize: Generalisieren der Erklärung; bestimme also hinreichende Bedingungen unter denen die gefundene Erklärungsstruktur gültig ist.</li> </ol> Bei der EBG werden also Makro-Operatoren erzeugt. Ein Beispiel für Software welche EBG benutzt ist <abbr title="STanford Resarch Institute Problem Solver">STRIPS</abbr>. </dd> <dt><dfn>KBANN</dfn> (<dfn>Knowledge-Based Artificial Neural Networks</dfn>)</dt> <dd>KBANN ist ein hybrides Verfahren. Die Idee ist ein neuronales Netz geschickt zu konstruieren. Dieses wird dann wie gewohnt mit Gradient Descent durch Trainingsbeispiele verfeinert. Der Algorithmus gibt eine Netzarchtiktur vor: <ul> <li>Dabei wird pro Instanzattribut ein Netz-Input verwendet. Für jede Klausel wird ein Neuron hinzugefügt.</li> <li>Dieses ist mit dem Instanzattribut durch das Gewicht \(w\) verbunden wenn es nicht negiert ist, sonst durch das Gewicht \(-w\).</li> <li>Der Schwellwert der Aktivierungsfunktion wird auf \(-(n- 0.5)w\) gesetzt, wobei \(n\) die Anzahl der nicht-negierten Bedingungsteile ist.</li> <li>Verbinde die restlichen Neuronen von Schicht \(i\) mit Schicht \(i+1\) indem zufällige kleine Gewichte gesetzt werden.</li> </ul> Angewendet werden kann KBANN: <ul> <li>Lernen von physikalischen Objektklassen</li> <li>Erkennung von biologischen Konzepten in DNS-Sequenzen</li> </ul> </dd> </dl> <h3 id="a-nameunsupervised-learninga-unberwachte-lernverfahren"><a name="unsupervised-learning"></a> Unüberwachte Lernverfahren</h3> <p>Slides: <code>MLI_14_UnueberwachtesLernen_slides1.pdf</code></p> <dl> <dt><dfn>\(k\)-means Clustering</dfn></dt> <dd>Der \(k\)-means Clustering Algorithmus finden \(k\) Cluster in einem Datensatz. Dabei ist \(k \in \mathbb{N}_{\geq 1}\) vom Benutzer zu wählen. Zuerst initialisert \(k\)-means die Zentroiden, also zentrale Punkte für Cluster, zufällig. Dann geht \(k\)-means geht iterativ vor: <ol> <li>Weise jeden Datenpunkt seinem nächsten Cluster zu.</li> <li>Verschiebe die \(k\) Zentroide in ihr Clusterzentrum</li> </ol> Siehe auch: <a href="//martin-thoma.com/k-nearest-neighbor-classification-interactive-example/">Interaktives Beispiel</a> </dd> <dt><dfn>Fuzzy \(k\)-means</dfn></dt> <dd>Im Gegensatz zum \(k\)-means Algorithmus, wo jeder Datenpunkt in genau einem Cluster ist, weißt der Fuzzy \(k\)-means Algorithmus jedem Datenpunkte eine Zugehörigkeitswahrscheinlichkeit zu. Je weiter der Datenpunkt vom Zentroid entfernt ist, desto unwahrscheinlicher wird die Zugehörigkeit. Die Cluster-Zugehörigkeit des Datenpunktes \(x_i\) zum Cluster \(c_j\) kann als Wahrscheinlichkeit in Abhängigkeit der Distanz \[d_{ij} = |x_i - z_j|^2\] zum Zentroiden \(z_j\) ausgedrückt werden: \[P(c_j | x_i) = \frac{(\frac{1}{d_{ij}})^{\frac{1}{b-1}}}{\sum_{r=1}^k (\frac{1}{d_{ir}})^{\frac{1}{b-1}}}\] wobei \(b \in \mathbb{R}_{\geq 1}\) ein frei zu wählender Parameter ist. Die Zentroide werden dann wie folgt neu berechnet: \[z_j = \frac{\sum_{i=1}^n [P(z_j|x_i)]^b \cdot x_i}{\sum_{i=1}^n [P(z_j | x_i)]^b}\] </dd> <dt><a href="https://de.wikipedia.org/wiki/Hierarchische_Clusteranalyse"><dfn>Hierarchisches Clustern</dfn></a></dt> <dd>Die Idee des hierarchischen Clusterns ist die iterative Vereinigung von Clustern zu größeren Clustern. Ergebisse können durch ein Dendrogramm beschrieben werden. Anwendung: Einordnung von Schrauben in ein Ordnungssystem </dd> <dt><dfn>Agglomerative Hierarchical Clustering</dfn> (<dfn>AHC</dfn>)</dt> <dd>AHC ist ein hierarchisches Clusteringverfahren. Dabei ist ein Clusterdistanz-Schwellwert \(t \in \mathbb{R}\) und eine minimale Cluster-Anzahl \(k \in \mathbb{N}\) zu wählen. Auch ein Distanzmaß für Cluster (nearest neighbor, farest neighor, mean distance, ...) ist als Hyperparameter zu wählen. Dann geht AHC wie folgt vor: <div class="highlight"> <pre><code class="language-text" data-lang="text"> c ← k # Minimale Anzahl an Clustern c' ← n # Anzahl der Datenpunkte # Weise jedem Punkt sein eigenes Clusterzentrum zu for i in range(1, n): D_i ← {x_i} # Vereinige Clusterzentren do: c' := c' -1 find closest clusters D_i, D_j if d(D_i, D_j) ⩽ t: merge(D_i, Dj) else: break until c = c' </code></pre> </div> </dd> <dt><a href="https://en.wikipedia.org/wiki/Conceptual_clustering"><dfn>Begriffliche Ballung</dfn></a></dt> <dd>Bei Algorithmen der Begrifflichen Ballung werden Konzeptbeschreibungen generiert.</dd> <dt><a href="https://en.wikipedia.org/wiki/Cobweb_(clustering)"><dfn>COBWEB</dfn></a></dt> <dd>Cobweb ist ein Algorithmus zur begrifflichen Ballung. Er lernt durch inkrementelles Aufbauen eines Strukturbaumes. Dabei sind nominale Attribute gestattet. Dabei wird ein Datenpunkt \(x_i\) zum Cluster \(c_j\) geclustert, wenn man die Attributwerte von \(x_i\) durch die Kentniss von \(c_j\) gut vorhersagen kann (<span>\(P(x_i | c_j)\)</span>, predictability) und zugleich der Cluster gut vorhergesagt werden kann, wenn die Attributwerte gegeben sind (<span>\(P(c_j|x_i)</span>, predictiveness). Es soll also in inter-Klassenähnlichkeit minimiert und die intra-Klassenähnlichkeit maximimiert werden. Dafür wird die Category Utility verwendet: <div> \[\text{CU} = \sum_{k=1}^K \sum_{i=1}^I \sum_{j=1}^{J(i)} P(A_i = V_{ij}) \cdot P(A_i = V_ij | C_k) \cdot P(C_k | A_i = V_{ij})\] </div> Dabei gilt: <ul> <li>\(K\): Anzahl der Cluster</li> <li>\(I\): Anzahl der Attribute</li> <li>\(J(i)\): Anzahl der Attributwerte des \(i\)-ten Attributs</li> <li>\(V_{ji}\): \(j\)-ter möglicher Wert für Attribut \(i\)</li> <li>\(P(A_i = V_ij | C_k)\): Predictability</li> <li>\(P(C_k | A_i = V_{ij}\): Predictiveness</li> </ul> Anwendung: Interpretation von <abbr title="Elektromyographie">EMGs</abbr> </dd> </dl> <h2 id="prfungsfragen">Prüfungsfragen</h2> <ul> <li>Was ist Induktives Lernen?<br /> → Eine große Menge an Beispielen wird gegeben. Der Lerner muss selbst das Konzept herausfinden.</li> <li>Was ist Deduktives Lernen?<br /> → Fakten werden gegeben. Der lernende bekommt das allgemeine Konzept gesagt und muss nur logische Schlussfolgerungen machen.</li> <li>SVMs <ul> <li>Wie funktioniert SRM bei SVMs?<br /> → Dualität zwischen Feature- und Hypothesenraum: Radius der Hyperkugel wird minimiert.</li> <li>Warum lernen SVMs "korrekt"?<br /> → Es gibt ein Theorem (TODO: Welches?) das besagt, dass die VC-Dimension eines Klassifiers, welcher Datenpunkte im \(n\)-Dimensionalen Raum innerhalb einer Kugel mit Radius \(D\) durch eine Hyperebene mit mindestens Abstand \(\Delta\) trennen will, durch \((\frac{D}{\Delta})^2\) beschränkt ist. Die SVM minimiert genau diesen Quotienten, da sie den Margin maximiert. Alternativ: Erklärung durch Strukturierung des Hypothesenraumes (TODO). </li> </ul> </li> <li>Reinforcement Learning <ul> <li>Wie lautet die Bellman-Gleichung?<br /> → \(Q(s, a) = r + \gamma \max_{a'} Q(s', a')\) wobei \(\gamma\) ein Diskontierungsfaktor ist, \(s'\) der Zustand in den man kommt, wenn man \(a\) ausführt und \(r\) der Reward nach ausführen von \(a\) in \(s\) ist.</li> <li>Was ist Value Iteration und wie lautet die Formel?<br /> → Schätzen der Value-Funktion durch iteratives anwenden von \(\hat{V}^*(s_t) \leftarrow r_t + \gamma \hat{V}^*(s_{t+1})\)</li> <li>Was sind Eligibility Traces im Kontext von Reinforcement Learning?<br /> → Siehe <a href="#rl-eligibility-trace">oben</a></li> <li>Wie funktioniert Q-Learning?<br /> → Siehe <a href="#q-learning">Abschnitt Q-Learning</a></li> </ul> </li> <li>Evolutionäre Algorithmen: Was ist wichtig? <ul> <li>Population / Individuen: Wie Individuen darstellen<br /> → Durch Gene (Attribute), z.B. als Bitstring</li> <li>Gegebener Ablauf (Wahl der Eltern, Generierung der Individuen)</li> <li>Wie kann man Kombinieren?<br /> → vgl. <i>Rekombination</i></li> <li>Fitness Function</li> <li>Was sind die wichtigsten Elemente von evolutionären Algorithmen?<br /> → Mutation, Rekombination, Fittness-Funktion, Selektion</li> <li>Was ist Landmarksche / Baldwinsche Evolution?</li> </ul> </li> <li>Wie lautet die Fehlerabschätzung von Vapnik?<br /> → Siehe <a href="#fehlerabschaetzung">Abschätzung des realen Fehlers</a> durch den empirischen Fehler und die VC-Dimension.</li> <li>Was versteht man unter Cascade Correlation?<br /> → <a href="https://www.youtube.com/watch?v=1E3XZr-bzZ4">YouTube</a> (4:05 min)</li> <li>Welche übwerwachten Lernverfahren gibt es?<br /> → Neuronale Netze, SVMs</li> <li>Wie funktioniert Inferenz in Markov Logik Netzen?<br /> → Siehe <a href="#mln-inference">oben</a></li> <li>Wie wird die Verbundwahrscheinlichkeit / Weltwahrscheinlichkeit in Markov Logik Netzen berechnet?<br /> → Siehe <a href="#mln-jpd">oben</a></li> <li>Was ist Dynamic Decay Adjustment (DDA)?<br /> → Siehe <a href="#dda-algorithm">oben</a></li> <li>Was ist erklärungsbasierte Generalisierung (EBG)?<br /> → Der Agent lernt keine neuen Konzepte, aber er lernt über Verbindungen bekannter Konzepte.</li> <li>Wie lautet die Formel für Entropie / Information Gain?<br /> → \(\text{Entropie} = - \sum_{i} p_i \log p_i\) und \(KL(P, Q) = \sum_{x \in X} P(x) \cdot \log \frac{P(x)}{Q(x)}\)</li> <li>Was ist Cobweb?<br /> → Siehe <a href="#unsupervised-learning">Unsupervised Learning</a></li> </ul> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://cg.ivd.kit.edu/lehre/ws2015/cg/index.php">Vorlesungswebsite</a></li> <li><a href="http://cg.ivd.kit.edu/lehre/ws2015/cg/uebung.php">Übungswebsite</a></li> <li>StackExchange <ul> <li><a href="http://datascience.stackexchange.com/q/8642/8820">What is the difference between concept learning and classification?</a></li> <li><a href="http://datascience.stackexchange.com/q/10000/8820">What is the difference between a (dynamic) Bayes network and a HMM?</a></li> </ul> </li> <li><a href="//martin-thoma.com/machine-learning-2-course/">Zusammenfassung der Vorlesung ML 2</a></li> <li>Udacity <ul> <li><a href="https://www.udacity.com/course/knowledge-based-ai-cognitive-systems--ud409">Knowledge-Based AI: Cognitive Systems</a>: Unter anderem gibt es eine Lektion zu Explanation-Based Learning (erklärungsbasierte Generalisierung)</li> </ul> </li> </ul> <h2 id="literatur">Literatur</h2> <ul> <li>[<a href="#ref-mit97-anchor" name="ref-mit97">Mit97</a>] T. Mitchell. Machine Learning. McGraw-Hill, 1997.</li> <li>[<a href="#ref-dar09-anchor" name="ref-dar09">Dar09</a>] A. Darwiche. Modeling and reasoning with Bayesian networks. Cambridge University Press, Cambridge [u.a.], 2009.</li> <li>[<a href="#ref-ber95-anchor" name="ref-ber95">Ber95</a>] M. Berthold and J. Diamond. Boosting the Performance of RBF Networks with Dynamic Decay Adjustment. Advances in Neural Information Processing, 1995. [<a href="http://kops.uni-konstanz.de/handle/123456789/5427">Online</a>]</li> <li>[<a href="#ref-pro06-anchor" name="ref-pro06">Pro06</a>] Prokopenko, Mikhail and Gerasimov, Vadim and Tanev, Ivan. Evolving Spatiotemporal Coordination in a Modular Robotic System. Springer, 2006.</li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <p>Es gibt keine Übungsblätter, keine Übungen, keine Tutorien und keine Bonuspunkte.</p> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Mündliche Prüfung (in Zukunft schriftlich)<br /> <strong>Ort</strong>: nach Absprache<br /> <strong>Zeit</strong>: 15 min<br /> <strong>Übungsschein</strong>: gibt es nicht<br /> <strong>Bonuspunkte</strong>: gibt es nicht<br /> <strong>Ergebnisse</strong>: werden ca. 5 - 10 min. nach der mündlichen Prüfung gesagt<br /> <strong>Erlaubte Hilfsmittel</strong>: keine</p> Wo ist Hörsaal 9 am KIT? //martin-thoma.com/wo-ist-hs9/ Mon, 02 Nov 2015 21:33:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wo-ist-hs9 <p>Dieser Artikel ist für all die verzweifelten Studienanfänger am <abbr title="Karlsruher Institut für Technologie">KIT</abbr>, die den Hörsaal 9 (HS 9) suchen.</p> <p>Der HS 9 ist in <a href="https://www.kithub.de/map/2264">Gebäude 20.40</a>, dem Architektengebäude. Es ist im ersten Stockwerk. Da muss man die große Treppe des Haupteingangs hoch, nach rechts abbiegen und um die Ecke laufen.</p> <p>Sinnigerweise ist Hörsaal 37 (HS 37) im Erdgeschoss…</p> <p>&amp;ast;sigh&amp;ast; da hätte ich wirklich gerne <a href="https://www.google.com/maps/about/partners/indoormaps/">Google Indoor Maps</a>. Oder zumindest im Ergeschoss einen Plan, der Pläne der Stockwerke beinhaltet. Am besten noch eine alphabetisch sortierte Liste der Räume mit Verweis auf die Etage…</p> <p>(Randnotiz: Falls sich jemand über diesen Mini-Artikel wundert: Ich habe diese Hörsäle schon mehrfach gesucht. Letzens wegen <a href="http://www.math.kit.edu/stoch/edu/statistik2015w/">Statistik</a>, wo das so wunderbar präzise auf der Vorlesungsseite steht… nun kann man es hoffentlich bald googeln, auch wenn ich nicht dabei unterstützt wurde, die Pläne auf Google Indoor Maps zu stellen. Irgendwas von “Datenschutz” wurde gesagt…)</p> Computergrafik - Klausur //martin-thoma.com/cg-klausur/ Fri, 23 Oct 2015 11:30:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cg-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Computergrafik&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://ies.anthropomatik.kit.edu/mitarbeiter.php?person=beyerer">Herrn Prof. Dr. Ing. Carsten Dachsbacher</a> im Wintersemester 2015/2016 gehört. Der Artikel ist noch am Entstehen.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="vorlesung">Vorlesung</h3> <table> <tr> <th>Datum</th> <th>Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>20.10.2015</td> <td>Einleitung</td> <td>Viele nette Bilder und Beispiele, wenig Inhalt</td> </tr> <tr> <td>22.10.2015</td> <td>Farbe, Darstellung &amp; Perzeption</td> <td><a href="https://de.wikipedia.org/wiki/Weber-Fechner-Gesetz">Weber-Fechner-Gesetz</a>, <a href="https://de.wikipedia.org/wiki/Nyquist-Shannon-Abtasttheorem">Abtasttheorem</a>, <a href="https://de.wikipedia.org/wiki/Dynamikumfang">Dynamikumfang</a>, Farbwahrnehmung im menschlichen Auge; <a href="https://de.wikipedia.org/wiki/Gammakorrektur">Gammakorrektur</a></td> </tr> <tr> <td>26.10.2015</td> <td>Übung</td> <td>gdb (bt - backtrace; p - print)</td> </tr> <tr> <td>26.10.2015</td> <td>&nbsp;</td> <td>Metamerismus: Unterschiedliche Spektren können gleichen Farbeindruck erwecken<br /> Addiere/subtrahiere Farbmischung<br /> <abbr title="Cyan, Magenta, Yellow">CMY</abbr> / <a href="https://de.wikipedia.org/wiki/CMYK-Farbmodell"><abbr title="Cyan, Magenta, Yellow, Key">CMYK</abbr></a> / <a href="https://de.wikipedia.org/wiki/RGB-Farbraum"><abbr title="Red Green Blue">RGB</abbr></a> / <abbr title="Hue Saturation Value">HSV</abbr> / <a href="https://de.wikipedia.org/wiki/CIE-Normvalenzsystem">XYZ</a><br /> <a href="https://de.wikipedia.org/wiki/Weber-Fechner-Gesetz">Weber-Fechner-Gesetz</a>: 2% heller </td> </tr> <tr> <td>29.10.2015</td> <td>Ray-Tracing: Kapitel 2</td> <td>Menschen nehmen Kontrastintensität und Luminenz besser als Chrominanz war. Das ermöglicht Kompression.<br /> clear-type / subpixel Darstellung<br /> Jaggies: Unerwünschter Treppenstufen-Effekt bei Rasterisierung von Strecken<br /> Kamera: Position (x,y,z), Blickrichtung (zu einem Punkt mit Koordinaten (x,y,z)) und up-Vektor<br /> Skalarprodukt, Kreuzprodukt<br /> <a href="https://de.wikipedia.org/wiki/Baryzentrische_Koordinaten">Baryzentrische Koordinaten</a>, </td> </tr> <tr> <td>02.11.2015</td> <td>Übung</td> <td>Rasterisierung von Linien (Implizite Darstellung)<br /> zbuffer: Tiefe des "nächsten" Polygons pro Pixel wird gespeichert<br /> Konsistenzregeln, z.B. wenn man zwei benachbarte farbige Dreiecke mit Diagonale hat und man die Farbe des Pixels berechnen muss, durch den beide Dreiecke teilweise gehen (37 Fälle; Katalog von Microsoft; macht die Hardware)</td> </tr> <tr> <td>26.11.2015</td> <td>?</td> <td><a href="https://en.wikipedia.org/wiki/Sphere_mapping">Sphere Mapping</a>; Vorfilterung von Environment Maps</td> </tr> <tr> <td>10.12.2015</td> <td>Räumliche Datenstrukturen</td> <td>BSP-Baum, kD-Baum</td> </tr> <tr> <td>14.01.2016</td> <td>OpenGL</td> <td>&nbsp;</td> </tr> <tr> <td>18.01.2016</td> <td>Übung</td> <td>Koordinatensystem-Pipeline, Shader</td> </tr> <tr> <td>19.01.2016</td> <td>Erzeugung von Landschaften</td> <td>Rotes / Rosa Rauschane, Lattice Value Noise, Perlin-Noise</td> </tr> </table> <h3 id="folien">Folien</h3> <h4 id="bilder-farbe-perzeption">Bilder, Farbe, Perzeption</h4> <p>Slide: <code>01_ Bilder, Farbe, Perzeption - Teil1.pdf</code></p> <dl> <dt><dfn>Frame Buffer</dfn></dt> <dd>Speichert Bilder zur direkten wiedergabe auf dem Bildschirm.</dd> <dt><dfn>Ditherhing</dfn></dt> <dd>TODO</dd> <dt><dfn>Dynamikumfang</dfn></dt> <dd>Der Dynamikumfang beschreibt den erreichbaren Kontrast eines Wiedergabegrätes (Bildschirm, Beamer): \[R_d = \frac{I_{\text{max} + k}}{I_{\text{min}} + k}\] TODO: Was ist \(k\)? Was ist \(I_{max} / I_{min}\)?</dd> <dt><dfn>Gamma-Korrektur</dfn></dt> <dd>TODO</dd> <dt><dfn>Transferfunktion</dfn></dt> <dd>TODO</dd> </dl> <p>Slide: <code>01_ Bilder, Farbe, Perzeption - Teil2.pdf</code></p> <dl> <dt><dfn>Additive Farmbischung</dfn></dt> <dd>Grundfarben: Rot, Grün, Blau<br /> Anwendung: Bildschirm</dd> <dt><dfn>Subtraktive Farbmischung</dfn></dt> <dd>Grundfarben: Cyan, Magenta, Gelb<br /> Anwendung: Drucker</dd> <dt><dfn>Graßmansche Gesetze</dfn></dt> <dd>Jeder Farbeindruck kann mit 3 Grundgrößen beschrieben werden.</dd> </dl> <ul> <li>RGB-Farbraum</li> <li>HSV-Farbraum</li> <li>CIE Color Matching Functions</li> <li>XYZ Color Space</li> <li>Chromatizität</li> <li>xyY Farbraum</li> <li>Weber-Fechner-Gesetz</li> <li>Machsche Streifen / Bandeffekte</li> <li>Hermann-Gitter / Laterale Hemmung</li> <li>Windows clear type / Subpixel</li> </ul> <h4 id="raytracing">Raytracing</h4> <p>Side: <code>02_ Raytracing (enthalt Abtastung aus Kapitel 1).pdf</code></p> <ul> <li>Nyquist-Shannon-Abtasttheorem</li> <li>Vektoren, Ortsvektoren, Skalarprodukt</li> <li>Parametrisierte Geraden- und Ebenendarstellung</li> <li>Baryzentrische Koordinaten</li> <li>Strahl-Kugel-Schnitt</li> <li>Spekulare Reflektion</li> <li>Diffuse (Lambertsche) Reflektion</li> <li>BRDF - Bidirectional Reflectance Distribution Function</li> <li>Phong Beleuchtungsmodell</li> <li>Snellsches Brechungsgesetz</li> <li>Fresnel-Effekt</li> <li>Anti-Aliasing Strategien: Uniformes Supersampling, Adaptives Supersampling, Stochastisches Supersampling</li> <li>Schattenstrahlen</li> <li>Bewegungs- und Tiefenunschärfe</li> <li>Imperfekte Spiegelung und Transmission</li> </ul> <h4 id="rumliche-datenstrukturen">Räumliche Datenstrukturen</h4> <p>Slide: <code>05_ Raumliche Datenstrukturen.pdf</code> (10.12.2015)</p> <ul> <li>Hüllkörper <ul> <li>Axis-Aligned Bounding Boxes (AABB)</li> <li>Bounding Volume Hierachies (BVH)</li> </ul> </li> <li>Reguläre Gitter</li> <li>Oktalbaum (Octree)</li> <li>kD-Baum</li> </ul> <dl> <dt><dfn>BSP-Baum</dfn></dt> <dd>TODO</dd> <dt><dfn>Surface Area Heuristics</dfn> (<dfn>SAH</dfn>)</dt> <dd>Schätzfunktion für die Oberfläche eines Objekts (TODO?).</dd> </dl> <h4 id="rasterisierung-clipping-und-projektionstransformationen">Rasterisierung, Clipping und Projektionstransformationen</h4> <p>Side: <code>06_ Rasterisierung, Clipping und Projektionstransformationen.pdf</code></p> <ul> <li>Tiefenpuffer, Z-Buffer</li> <li>Clipping</li> <li>Sutherland-Hodgeman Polygon Clipping</li> </ul> <h4 id="section">19.01.2016</h4> <dl> <dt><dfn>Perlin-Noise</dfn></dt> <dd>Zufallszahlen-Pool + Hash + Permutation</dd> <dt><dfn>Oktave</dfn></dt> <dd>Sammlung von Noise-Funktionen</dd> </dl> <h3 id="prfungsfragen">Prüfungsfragen</h3> <p>Kommt noch… spätestens wenn die Klausur naht.</p> <h3 id="bungen">Übungen</h3> <h4 id="blatt-1">Blatt 1</h4> <p>Das Framework bekommt man ohne VM unter Ubuntu 15.04 nach der Installtion folgender Pakete (vielleicht) zum laufen:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo apt-get install cmake xorg-dev libglu1-mesa-dev freeglut3 freeglut3-dev libglew1.5 libglew1.5-dev libglu1-mesa libglu1-mesa-dev libgl1-mesa-glx libgl1-mesa-dev libglfw3 </pre></div> </div> </div> <p>Wenn ihr den Fehler</p> <blockquote> <p>error adding symbols: DSO missing from command line ubuntu</p> </blockquote> <p>bekommt, dann solltet ihr einfach die obigen Pakete installieren, den <code>build</code>-Ordner löschen und es neu versuchen.</p> <ul class="gallery mw-gallery-traditional" style="max-width: 489px; width: 489px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/11/color-cube.png" class="image"><img src="//martin-thoma.com/captions/color-cube.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Color cube</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/11/gravity-field.png" class="image"><img src="//martin-thoma.com/captions/gravity-field.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Gravity field</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/11/temperature.png" class="image"><img src="//martin-thoma.com/captions/temperature.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Temperature of a black body</div></div></li></ul> <p>Außerdem:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pacman -Syy </pre></div> </div> </div> <p>ausführen. Dann bekommt man auch nicht mehr 404er wenn man mit</p> <pre><code>$ pacman -S vim </code></pre> <p>vim installieren will.</p> <p>In der VM sollte unter Settings → System → Acceleration die Option “Enable VT-x/AMD-V” aktiviert sein. Zusätzlich sollte im BIOS des Host-Systems (also von eurem Rechner) die “Intel Virtualization Technology” aktiviert sein. (Man Laptop hat das nicht - bei mir funktionieren die Beispiele in der VM aber auch nicht :-/)</p> <h4 id="blatt-6">Blatt 6</h4> <ul> <li><a href="http://glm.g-truc.net/0.9.0/api/a00192.html">glm::gtx::transform</a></li> </ul> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://cg.ivd.kit.edu/lehre/ws2015/cg/index.php">Vorlesungswebsite</a></li> <li><a href="http://cg.ivd.kit.edu/lehre/ws2015/cg/uebung.php">Übungswebsite</a></li> <li><a href="https://lists.ira.uni-karlsruhe.de/mailman/listinfo/cg.cg">E-Mail Verteiler</a></li> </ul> <p>Siehe auch</p> <ul> <li><a href="http://www.codinglabs.net/article_world_view_projection_matrix.aspx">World, View and Projection Transformation Matrices</a></li> <li><a href="http://stackoverflow.com/questions/18019968/how-to-calculate-transformation-matrix">How to calculate transformation matrix</a></li> <li>OpenGL <a href="http://www.opengl-tutorial.org/beginners-tutorials/tutorial-3-matrices/">Tutorial 3 : Matrices</a></li> </ul> <h2 id="literatur">Literatur</h2> <ul> <li>P. Shirley, S. Marschner: Fundamentals of Computer Graphics, 3rd Edition<br /> → Kapitel 3-4, Kapitel 7-9, Kapitel 11-12 (Data Structures for Graphics)</li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <p>Es gibt Übungsblätter und Übungen, aber keine Tutorien und keine Bonuspunkte.</p> <p>Um das Modul zu bestehen wird der Übungsschein benötigt. Für den Übungsschein benötigt man 60% der Punkte der Übungsblätter. Die Übungsblätter werden über <a href="https://submit.ivd.kit.edu/main/index.php">submit.ivd.kit.edu</a> eingereicht. Die Übungsblätter erscheinen alle 2 Wochen. Es gibt also min. 6 Übungsblätter und min. 120 Punkte. Die Deadline ist Montag, 11:00.</p> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Mittwoch, der 09.03.2015 von 14:00 Uhr (Quelle: <a href="http://www.informatik.kit.edu/klausuren.php?kid=546.35">informatik.kit.edu</a>)<br /></p> <ul> <li>08.02.2016: Die Klausur-Anmeldung wird freigeschalten</li> <li>04.03.2016: Anmeldeschluss</li> <li>06.03.2016: Abmeldeschluss</li> </ul> <p><strong>Ort</strong>: <a href="https://www.kithub.de/map/2086">10.21 (Daimler und Benz)</a><br /> <strong>Punkte</strong>: ?<br /> <strong>Zeit</strong>: ? min<br /> <strong>Punkteverteilung</strong>: ?<br /> <strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: ?<br /> <strong>Bonuspunkte</strong>: ?<br /> <strong>Ergebnisse</strong>: ?<br /> <strong>Einsicht</strong>: Noch nicht bekannt (Stand: 23.10.2015)<br /> <strong>Erlaubte Hilfsmittel</strong>: keine</p> Rename Script //martin-thoma.com/rename-script/ Wed, 16 Sep 2015 16:15:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/rename-script <p>Once in a while I have to bulk rename files. For example, when I have holiday photos. The following script helps me to do so:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Batch-Rename files in a folder according to some rules.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">rename</span>(rename, starts=<span style="color:#069">None</span>, ends=<span style="color:#069">None</span>, test=<span style="color:#069">False</span>): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> Rename all files which end with `ends` and start with `starts` to</span><span> </span><span> `rename-[Number]`.</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> files = [f <span style="color:#080;font-weight:bold">for</span> f <span style="color:#080;font-weight:bold">in</span> os.listdir(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">.</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">if</span> os.path.isfile(f)] <span style="color:#777"># Sort files by last modification</span> files.sort(key=<span style="color:#080;font-weight:bold">lambda</span> x: os.stat(x).st_mtime) <span style="color:#080;font-weight:bold">if</span> starts <span style="color:#080;font-weight:bold">is</span> <span style="color:#080;font-weight:bold">not</span> <span style="color:#069">None</span>: files = [f <span style="color:#080;font-weight:bold">for</span> f <span style="color:#080;font-weight:bold">in</span> files <span style="color:#080;font-weight:bold">if</span> f.lower().startswith(starts.lower())] <span style="color:#080;font-weight:bold">if</span> ends <span style="color:#080;font-weight:bold">is</span> <span style="color:#080;font-weight:bold">not</span> <span style="color:#069">None</span>: files = [f <span style="color:#080;font-weight:bold">for</span> f <span style="color:#080;font-weight:bold">in</span> files <span style="color:#080;font-weight:bold">if</span> f.lower().endswith(ends.lower())] <span style="color:#080;font-weight:bold">for</span> i, f <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(files, start=<span style="color:#00D">1</span>): filename, ext = os.path.splitext(f) ext = ext.lower() new_name = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">%s-%i%s</span><span style="color:#710">&quot;</span></span> % (rename, i, ext) <span style="color:#080;font-weight:bold">if</span> test: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">{0:&lt;40}-&gt; {1:&lt;20}</span><span style="color:#710">&quot;</span></span>.format(f, new_name)) <span style="color:#080;font-weight:bold">else</span>: os.rename(f, new_name) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">get_parser</span>(): <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span>, <span style="color:#B44;font-weight:bold">ArgumentDefaultsHelpFormatter</span> parser = ArgumentParser(description=__doc__, formatter_class=ArgumentDefaultsHelpFormatter) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-n</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--name</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">name</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">new name</span><span style="color:#710">&quot;</span></span>, required=<span style="color:#069">True</span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">NAME</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-s</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--starts</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">starts</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Get files which start with this string</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#069">None</span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">STARTS</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-e</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--ends</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">ends</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Get files which end with this string</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#069">None</span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">ENDS</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-t</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--test</span><span style="color:#710">&quot;</span></span>, action=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">store_true</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">test</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#069">False</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">don't change anything, just show what would be </span><span style="color:#710">&quot;</span></span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">done</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">return</span> parser <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: args = get_parser().parse_args() rename(args.name, starts=args.starts, ends=args.ends, test=args.test) </pre></div> </div> </div> Languages for Back Ends //martin-thoma.com/languages-for-back-ends/ Wed, 24 Jun 2015 12:43:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/languages-for-back-ends <p>What programming language would I use for the back end of a big, new project in a startup which wants to offer a web service? Sure, on the client side there is pretty much only JavaScript (including variants like <a href="http://en.wikipedia.org/wiki/CoffeeScript">CoffeeScript</a> and <a href="http://en.wikipedia.org/wiki/TypeScript">TypeScript</a>) in combination with HTML and CSS. I’ve used <a href="http://en.wikipedia.org/wiki/MySQL">MySQL</a> and <a href="http://en.wikipedia.org/wiki/Redis">Redis</a> databases and I’m quite happy with that. But the choice for the server side is not that easy. I’ve been using PHP for quite a while now, because it was the cheapest and easiest choice when I started programming. But things have changed (and I have more money, so I don’t have to take the super cheap hosting services). Although my experience with web projects is very limited, I want to share a few thoughts.</p> <h2 id="definitions-back-end-and-security">Definitions: Back End and Security</h2> <p>Just for clarification: I am only talking about the back end. A back end is the data access layer which manages requests comming to the server. It needs to server <strong>many requests</strong> (&gt; 100 requests/second) <strong>fast</strong> (&lt; 300 ms in average). It should not execute computationally heavy jobs which can be pre-computed or do not need to be displayed instantly to the client. This can be done by another system which does not need to be programmed in the same language. The back end does also not deal with presentation to the user. This is what the front end does. However, you should have more than a good idea in which form the front end gets the data. The cleanest approach I’ve seen so far is a pure RESTful API for all interactions between front end and back end.</p> <p>The backend language should also make it easy to validate / sanitize input data, connect with databases, store/get stuff on/from the file system.</p> <p>In the following, I will write that some languages are “secure” or “not secure”. This does not mean that you can / cannot write code which is secure. It means that the compiler (or other widespread tools) give you guarantees about bugs in your code. For example, C is a very insecure language as the compiler does no <a href="https://en.wikipedia.org/wiki/Bounds_checking">bounds checking</a>. The types of errors which can be detected by automatic tools (without further testing) are:</p> <ul> <li>Syntax errors,</li> <li>Out of bounds (reading),</li> <li><a href="https://en.wikipedia.org/wiki/Buffer_overflow">buffer overflow</a> (not checked in C/C++, but not possible in Java (<a href="http://stackoverflow.com/q/479701/562769">source</a>)),</li> <li>unused variables (which might indicate other problems; at least code smell),</li> <li>type problems: This is a bit fuzzy, as you can write stringly typed code (see <a href="http://blog.codinghorror.com/new-programming-jargon/">New Programming Jargon</a>) in probably every language, but in some languages it is more common than in others. Some languages also make it easier to use the type system to detect errors. For example, PHP is very insecure in this sense as <code>123 == "123ab"</code>, Python is a bit more secure, but you can return whatever you want, Java is much more secure. Haskell is even more secure in this sense, as it has real functions (without side effects, checked by the compiler). See <a href="http://programmers.stackexchange.com/q/167975/25699">What can Haskell’s type system do that Java’s can’t and vice versa?</a> for more.</li> </ul> <p>There are also some errors which can be detected at runtime. The handling of those runtime errors differs from language to language. For example, C and C++ fails silently (e.g. <a href="http://stackoverflow.com/q/671703/562769">this question</a>). This is bad. For example, there are some silent out-of-bounds errors in C / C++ where Rust would fail loud (I think Heartbleed is one example; see <a href="http://tonyarcieri.com/would-rust-have-prevented-heartbleed-another-look">Would Rust have prevented Heartbleed? Another look</a> if you’re interested in that specific example).</p> <p>Of course, all of those problems can be detected with good testing. But the more is done automatically, the less can go wrong when you don’t write (good) tests.</p> <h2 id="java">Java</h2> <p><a href="http://en.wikipedia.org/wiki/Java_(programming_language)">Java</a> is an object-oriented language which runs on the Java Virtual Machine. Java is probably the most used language for big business websites. Why is that the case?</p> <ul> <li>Java is old: It first appeared in 1995. <ul> <li>Java is taught at many universities and many people know at least a little bit of Java. So companies don’t have problems finding developers. At least that might be the impression of people who don’t realize that there is a big differencee between people saying they know Java and developers who can actually work with it.</li> <li>I guess the Java ecosystem is pretty mature: <ul> <li><a href="http://en.wikipedia.org/wiki/Eclipse_%28software%29">eclipse</a>, <a href="http://en.wikipedia.org/wiki/IntelliJ_IDEA">IntelliJ IDEA</a> and <a href="https://en.wikipedia.org/wiki/NetBeans">Netbeans</a> as IDEs,</li> <li><a href="http://en.wikipedia.org/wiki/Jenkins_(software)">Jenkins</a> for continuous integration,</li> <li><a href="http://en.wikipedia.org/wiki/GlassFish">GlassFish</a>,</li> <li><a href="http://en.wikipedia.org/wiki/Apache_Ant">Apache Ant</a>/<a href="https://en.wikipedia.org/wiki/Apache_Maven">Apache Maven</a> or <a href="https://gradle.org/">Gradle</a> for automatic building,</li> <li><a href="http://en.wikipedia.org/wiki/JUnit">JUnit</a>, <a href="https://en.wikipedia.org/wiki/Mockito">Mockito</a>, Powermock for automatic unit tests,</li> <li><a href="http://en.wikipedia.org/wiki/Log4j">log4J</a> and <a href="http://logging.apache.org/log4j/2.x/">log4J 2</a> for logging,</li> <li><a href="https://en.wikipedia.org/wiki/Apache_JMeter">Apache JMeter</a> for load testing</li> <li><a href="https://jersey.java.net/">Jersey</a> for RESTful Web services,</li> <li><a href="https://en.wikipedia.org/wiki/Apache_Tomcat">Apache Tomcat</a> / <a href="https://en.wikipedia.org/wiki/WildFly">WildFly</a> (former JBoss): application server / web server / servlet container</li> <li><a href="https://grizzly.java.net/">Grizzly</a> / <a href="https://en.wikipedia.org/wiki/Jetty_(web_server)">Jetty</a>: Web server</li> <li><a href="http://findbugs.sourceforge.net/">FindBugs</a>, <a href="https://en.wikipedia.org/wiki/SonarQube">SonarQube</a> for code quality / static code analysis</li> <li><a href="https://en.wikipedia.org/wiki/Hibernate_(Java)">Hibernate</a> for ORM,</li> <li><a href="https://en.wikipedia.org/wiki/OSGi#Architecture">OSGi</a>: <a href="https://en.wikipedia.org/wiki/Apache_Felix">Apache Felix</a> / <a href="https://en.wikipedia.org/wiki/Equinox_(OSGi)">Equinox</a> - see <a href="https://www.youtube.com/watch?v=3Ut_3u4aVZQ">10min clip</a> for a high-level explanation of OSGi,</li> <li>Frameworks like <a href="https://en.wikipedia.org/wiki/Spring_Framework">Spring</a>, <a href="https://en.wikipedia.org/wiki/JavaServer_Faces">JSF</a>, <a href="http://en.wikipedia.org/wiki/JavaServer_Pages">JSP</a>, <a href="https://en.wikipedia.org/wiki/Apache_Struts_2">Apache Struts 2</a>, <a href="https://en.wikipedia.org/wiki/Apache_Wicket">Apache Wicket</a></li> </ul> </li> </ul> </li> <li>Java is developed by <a href="http://en.wikipedia.org/wiki/Oracle_Corporation">Oracle</a>. Hence you can make contracts with Oracle to get support when things don’t work.</li> </ul> <p>That was what we have on the positive side. What is not so good about Java?</p> <ul> <li>VERY clumsy syntax. This is more than just a inconvenience. You have to type a lot to get things done which makes you slow. Of course, you can (and need to) use autocompletion, but it is still a lot to read. That makes maintaining the code a mess.</li> <li>Tools are hard to get to work.</li> <li>Unnecessary super-abstract constructs used for eventually never happening future extensions (see <a href="http://geek-and-poke.com/geekandpoke/2014/1/2/games-for-the-real-geeks-part-2">Geek-and-poke.com</a>).</li> <li>A bit more secure than C/C++ as you cannot access out-of-bound arrays, you don’t have pointers. So buffer overflows are almost impossible in Java (see <a href="http://stackoverflow.com/a/479738/562769">SO</a> for more details). However, you buy this security with much less easy syntax and you don’t get as much security as would be possible with just a bit more effort. See rust for more details.</li> <li>Speed and memory usage: Again, Java might be better in speed than many other languages, but not as good as some others are. And Java seems to need A LOT of memory. However, I am not too sure if that is really a problem. (see <a href="http://www.infoworld.com/article/2609675/java/surprise--java-is-fastest-for-server-side-web-apps.html">Surprise! Java is fastest for server-side Web apps</a>)</li> </ul> <p>See also:</p> <ul> <li><a href="http://stackoverflow.com/a/1326084/562769">Is Java a Compiled or an interpreted programming language?</a>: The short answer is no. But Java guys don’t like to hear that ☺</li> <li><a href="http://security.stackexchange.com/q/57646/3286">Why do I hear about so many Java insecurities? Are other languages more secure?</a>: The short answer is no, thinking about C/C++.</li> <li><a href="http://security.stackexchange.com/q/32822/3286">Security of JVM for Server</a></li> <li><a href="http://stackoverflow.com/q/145110/562769">C++ performance vs. Java/C#</a></li> </ul> <h2 id="javascript-nodejs">JavaScript: Node.js</h2> <p><a href="http://en.wikipedia.org/wiki/Node.js">Node.js</a> is a runtime environment which was initially released in 2009 and became quite popular since then. Node.js is asynchronous, event-driven and scalable. Node.js applications are written in JavaScript and hence have all the advantages of JavaScript:</p> <ul> <li>They profit from heavy development in JavaScript engines / JIT compilers like <a href="http://en.wikipedia.org/wiki/V8_(JavaScript_engine)">V8</a>.</li> <li>The syntax is flexible and light-weight.</li> <li>Just like Java, JavaScript first appeared in 1995. So the language itself is old and stable. <ul> <li>A lot of developers know at least a little bit of JavaScript.</li> <li>The ecosystem is mature. <ul> <li><a href="http://en.wikipedia.org/wiki/Npm_(software)">npm</a> and <a href="http://en.wikipedia.org/wiki/Bower_(software)">bower</a> for package management</li> <li><a href="http://en.wikipedia.org/wiki/Backbone.js">Backbone.js</a> / <a href="http://en.wikipedia.org/wiki/AngularJS">AngularJS</a> for MVP / MVC.</li> <li><a href="http://en.wikipedia.org/wiki/Unit.js">Unit.js</a> for unit testing.</li> <li><a href="http://gruntjs.com/">Grunt</a> as a task runner.</li> <li><a href="http://docs.sequelizejs.com/en/latest/">Sequelize</a> as an ORM.</li> <li><a href="http://karma-runner.github.io/0.12/index.html">Karma</a>: Test runner</li> <li><a href="http://expressjs.com/">expressjs</a>: web application framework</li> </ul> </li> </ul> </li> <li><a href="http://stackoverflow.com/q/2353818/562769">Lots of easy tutorials</a></li> </ul> <p>What is still to say?</p> <ul> <li>Node is FAST and scalable! (see <a href="http://java.dzone.com/articles/performance-comparison-between">Performance Comparison Between Node.js and Java EE</a>)</li> <li>JavaScript is very insecure. Even simple syntax error will only get revealed when they are actually executed. So Unit testing is very important.</li> <li>Node.js is used by LinkedIn, Yahoo!, Uber, PayPal (<a href="https://nodejs.org/industry/">source</a>)</li> <li>There are quite a few people moving from Node.js to Go (<a href="http://thenewstack.io/from-node-js-to-go-why-one-startup-made-the-switch/">1</a>, <a href="http://bowery.io/posts/Nodejs-to-Golang-Bowery/">2</a>, <a href="http://zef.me/blog/6191/the-march-towards-go">3</a>, <a href="https://medium.com/code-adventures/farewell-node-js-4ba9e7f3e52b">4</a>)</li> </ul> <p>See also:</p> <ul> <li><a href="http://stackoverflow.com/q/5062614/562769">How to decide when to use Node.js?</a></li> <li><a href="http://stackoverflow.com/q/1911015/562769">How to debug Node.js applications</a></li> <li><a href="https://www.airpair.com/javascript/node-js-tutorial">node.js tutorial</a></li> </ul> <h2 id="go">Go</h2> <p><a href="https://en.wikipedia.org/wiki/Go_(programming_language)">Go</a> is a statically-typed, compiled language developed by Google. It first appeared in 2009, so it is very young.</p> <ul> <li>Go offers the basic tools you need for web development: <ul> <li><a href="http://martini.codegangsta.io/">martini</a>/ <a href="https://gin-gonic.github.io/gin/">Gin Gonic</a>: A web development framework</li> <li><a href="https://github.com/hoisie/mustache">mustache</a> for templates</li> <li><a href="https://github.com/jinzhu/gorm">gorm</a>: ORM</li> </ul> </li> <li><a href="https://tour.golang.org/">Good tutorial</a> and also some <a href="https://golang.org/doc/articles/wiki/">material for web development</a></li> <li>Some tasks are much more complicated than they should be. Sorting, to name one example (see <a href="http://stackoverflow.com/q/28999735/562769">SO</a>).</li> <li>Go is different from some other languages, e.g. if you want a method to be public, the first character of the method name has to be capitalized. Or unused variables result in a compiler error.</li> </ul> <p>See also:</p> <ul> <li><a href="https://www.dougcodes.com/go-lang/gin-gonic-may-be-40x-faster-than-martini-but-it-is-not-better">Gin Gonic May Be 40x Faster Than Martini, But It Is Not Better</a></li> <li><a href="https://www.reddit.com/r/golang/comments/1ye3z6/go_vs_nodejs_for_servers/">Go vs Node.js for servers</a></li> </ul> <h2 id="c35">C#</h2> <p><a href="https://en.wikipedia.org/wiki/C_Sharp_(programming_language)">C#</a> is a compiled, statically typed language (with dynamic features, see <a href="https://visualstudiomagazine.com/articles/2011/02/01/understanding-the-dynamic-keyword-in-c4.aspx">Understanding the Dynamic Keyword in C# 4</a>) developed by Microsoft. It was publically announced in 2000. The initial release of its web appliction framework <a href="https://en.wikipedia.org/wiki/ASP.NET">ASP.NET</a> was in 2002.</p> <p>The ecosystem seems to include:</p> <ul> <li><a href="http://www.nuget.org/">nuget.org</a></li> <li><a href="https://en.wikipedia.org/wiki/Internet_Information_Services">IIS</a>: Web server</li> <li><a href="http://www.asp.net/entity-framework">Entity Framework</a>: ORM</li> <li><a href="https://en.wikipedia.org/wiki/Language_Integrated_Query">LINQ</a>: SQL queries</li> <li><a href="https://en.wikipedia.org/wiki/Microsoft_Visual_Studio">Visual Studio</a>: IDE</li> <li><a href="https://en.wikipedia.org/wiki/ASP.NET_MVC_Framework">ASP.NET MVC Framework</a></li> </ul> <p>But I don’t know enough about C# / ASP.NET to write something meaningful about it.</p> <p>Coding Horror described why they use ASP.NET for StackOverflow and why he doesn’t recommend it for OpenSource projects (<a href="http://blog.codinghorror.com/why-ruby/">source</a>). StackExchange also describes what they use (<a href="http://blog.stackoverflow.com/2008/09/what-was-stack-overflow-built-with/">1</a>, <a href="http://meta.stackexchange.com/a/10370/158075">2</a>).</p> <p>I see a big problem in the Microsoft-centric technology stack. <strike>You have to use everything from them. (Almost) everything is closed source. If they discontinue the development or if they don't fix stuff which might be relevant for you, you're fucked.</strike></p> <p>This seems to change. Microsoft moved some important parts of their stack to GitHub (see <a href="http://dotnet.github.io/">dotnet.github.io</a>). Most important seems to be that the compiler Roslyn is licensed under an Apache License. But there is also ASP.NET, the Entity Framework, and the .NET runtime. The <a href="https://www.visualstudio.com/en-us/products/visual-studio-community-vs.aspx">Visual Studio Community Edition</a> is not available for free (but only for Windows).</p> <h2 id="python">Python</h2> <p><a href="https://en.wikipedia.org/wiki/Python_(programming_language)">Python</a> is one of the oldest programming languages which are still in use. It first appeared in 1991. Python is dynamically typed, interpreted, object-oriented and includes functional programming features.</p> <p>Although I use Python for many projects, I didn’t use it by now for a web project. So I might not know the important tools / frameworks. Please keep that in mind.</p> <ul> <li>Ecosystem: <ul> <li><a href="https://pypi.python.org/pypi">pypi.python.org</a> and <code>pip</code>: Package hosting and package management</li> <li><a href="http://sphinx-doc.org/">Sphinx</a>: (Semi) automatic code documentation, e.g. the <a href="http://docs.scipy.org/doc/scipy/reference/optimize.html">scipy docs</a> are generated with Sphinx from Python code. This is one of the best documentations I have ever seen.</li> <li><a href="https://en.wikipedia.org/wiki/Django_(web_framework)">Django</a>/ <a href="https://en.wikipedia.org/wiki/Flask_(web_framework)">Flask</a> as frameworks</li> <li><a href="http://pytest.org/latest/">pytest</a>/<a href="https://nose.readthedocs.org/en/latest/">nose</a> for testing</li> <li><a href="http://www.gevent.org/">gevent</a>: a coroutine-based Python networking library</li> <li><a href="http://www.tornadoweb.org/en/stable/">Tornado</a>: Web server</li> </ul> </li> <li>Some Python people switch to Go (<a href="https://lincolnloop.com/blog/djangonaut-building-webapp-go-gorilla/">1</a>, <a href="http://blog.disqus.com/post/51155103801/trying-out-this-go-thing">2</a>)</li> <li>Many tutorials and often very good documentation: <ul> <li><a href="http://flask.pocoo.org/">Flask</a></li> <li><a href="http://www.djangobook.com/en/2.0/index.html">djangobook.com</a> and <a href="https://docs.djangoproject.com/en/dev/intro/tutorial01/">docs.djangoproject.com</a></li> <li><a href="http://www.fullstackpython.com/">fullstackpython.com</a></li> </ul> </li> <li>Flask and Django work with PyPy (<a href="http://pypy.org/compat.html">source</a>). That might make them much faster.</li> <li>Used by big players: <ul> <li>Quora (<a href="http://www.quora.com/Why-did-Quora-choose-Python-for-its-development">source</a>)</li> <li>Prezi, Pinterest, Instagram (<a href="https://wakatime.com/blog/25-pirates-use-flask-the-navy-uses-django">source</a>)</li> <li>Bitbucket, The Onion (<a href="http://codecondo.com/popular-websites-django/">source</a>)</li> </ul> </li> </ul> <p>I think one of the main advantages of Python is that it is really easy to write code which is easy to read (because of docstrings, Pythons weird intendation semantics and very nice syntax) and quite hard to write unreadable code. I am sure I have a biased view regarding Python, but I am also sure a lot of people share this subjective impression.</p> <h2 id="php">PHP</h2> <p><a href="https://en.wikipedia.org/wiki/PHP">PHP</a> is a server-side scripting language which appeared first in 1995. It is dynamically typed.</p> <ul> <li><a href="//martin-thoma.com/php-a-strange-language/">Language inconsistencies</a> are really bad with PHP - see also <a href="http://eev.ee/blog/2012/04/09/php-a-fractal-of-bad-design/">PHP: a fractal of bad design</a></li> <li>The ecosystem is ok: <ul> <li><a href="https://www.phptesting.org/">PHPCI</a> for continuus integration.</li> <li><a href="https://en.wikipedia.org/wiki/Zend_Framework">Zend Framework</a> / <a href="https://en.wikipedia.org/wiki/Symfony">Symfony</a></li> <li>Smaller Frameworks like <a href="http://cakephp.org/">CakePHP</a> and <a href="http://www.codeigniter.com/">Code Igniter</a></li> <li><a href="https://en.wikipedia.org/wiki/Drupal">Drupal</a> / <a href="https://en.wikipedia.org/wiki/Joomla">Joomla</a> / <a href="https://en.wikipedia.org/wiki/TYPO3">TYPO3</a> / <a href="https://en.wikipedia.org/wiki/WordPress">WordPress</a></li> <li><a href="https://en.wikipedia.org/wiki/PHPUnit">PHPUnit</a> for unit testing,</li> <li><a href="https://en.wikipedia.org/wiki/Composer_(software)">Composer</a> for package management and <a href="https://packagist.org/">packagist.org</a> to find packages</li> <li><a href="http://cruisecontrol.sourceforge.net/">cruisecontrol</a> for Continuus Integration</li> </ul> </li> </ul> <p>A big advantage of PHP is that it is easy to learn. You can run PHP everywhere and hosting is cheap. Wikipedia makes use of PHP, so it is obviously possible to create systems which have HUGE numbers of requests and still work fine.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/Strip-PHP-doute650-Webenglsih.jpg"><img src="//martin-thoma.com/captions/Strip-PHP-doute650-Webenglsih.jpg" alt="The right tool for the right job" width="500" height="742" class="" /></a><p class="wp-caption-text">The right tool for the right job - by <a href="http://www.commitstrip.com/en/2015/01/12/the-right-tool-for-the-right-job/">commitstrip.com</a></p></div> <h2 id="hack">Hack</h2> <p><a href="https://en.wikipedia.org/wiki/Hack_(programming_language)">Hack</a> is a programming language introduced in 2014 by Facebook. It is a PHP dialect. Key differences to PHP are:</p> <ul> <li>Function arguments and return values can be annotated with types.</li> <li>Hack does not support some language features which are supported by PHP (<a href="http://docs.hhvm.com/manual/en/hack.unsupported.php">source</a>). Which is good. For example, goto, variable variables, string incrementing, …</li> </ul> <p>See also:</p> <ul> <li><a href="http://hacklang.org/">hacklang.org</a></li> </ul> <h2 id="rust">Rust</h2> <p>Rust is a very safe language, but seems not to be ready for productive usage.</p> <blockquote> <p>I am a big fan of Rust, but as it aims to be a better C++, it is probably a better fit for OS development, game engines, embedded systems, databases, complex desktop applications (Photoshop/Word/Chrome), etc. While Rust is quite expressive for a systems programming language, its banner features are the borrow checker (+ lifetimes, etc) and powerful static type system. Rust emphasizes zero-cost abstractions with compiler-enforced memory &amp; thread safety. The popular web development languages are dynamically typed and interpreted, with an emphasis on rapid development, which is a very different niche than Rust claims to fill.</p> </blockquote> <p>Source: <a href="https://news.ycombinator.com/item?id=7809791">news.ycombinator.com</a></p> <p>See:</p> <ul> <li><a href="http://arewewebyet.com/">arewewebyet.com</a></li> <li><a href="http://stackoverflow.com/a/23577767/562769">Rust Web Frameworks</a></li> </ul> <h2 id="others">Others</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Ruby_(programming_language)">Ruby</a> with <a href="http://en.wikipedia.org/wiki/Ruby_on_Rails">Rails</a>: I know it is quite well-known and used by many people. But I don’t know Ruby enough to write anything meaningful. The Ruby syntax is similar to Python.</li> <li><a href="https://en.wikipedia.org/wiki/Scala_(programming_language)">Scala</a> <a href="http://readwrite.com/2011/06/06/cpp-go-java-scala-performance-benchmark">seems to be noteworthy</a></li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="http://www.techempower.com/benchmarks/#section=data-r9&amp;hw=i7&amp;test=json">Web Framework Benchmarks</a></li> <li><a href="http://w3techs.com/technologies/overview/programming_language/all">Usage of server-side programming languages for websites</a></li> <li><a href="http://www.todobackend.com/">todobackend.com</a>: A lot of different back end technology stacks</li> <li><a href="https://www.bento.io/">bento.io</a>: Seems to offer many tutorials</li> <li><a href="http://redmonk.com/sogrady/2015/01/14/language-rankings-1-15/">The RedMonk Programming Language Rankings: January 2015</a></li> <li><a href="https://en.wikipedia.org/wiki/Comparison_of_programming_languages">Comparison of programming languages</a></li> </ul> <h2 id="conclusion">Conclusion</h2> <p>Thinking about it that carefully, I see three languages which seem to be suitable for back ends for me:</p> <ul> <li>Go: Fast and compiled</li> <li>node.js: Good scalability</li> <li>Python: It is the language I know best and of which I like the syntax best. Besides that, it has a very nice and clear syntax, good community-developed coding style standards and is very easy to read and well-documented.</li> </ul> <p>Not suitable seem to be:</p> <ul> <li>PHP: Because of the language inconsistencies which seem to make it pretty hard to make a reliable back end</li> <li>C#: The technology stack is too Microsoft centered.</li> <li>Java: Too clumsy syntax, too hard to get it work.</li> </ul> <p>The other programming languages could be very good choices. I simply don’t know it. I am very curious if rust will be used for back ends. Hack is very young, let’s see if it will spread in a few years.</p> <h2 id="credits">Credits</h2> <p>As I don’t have much experience with web development, I asked a few friends to have a look at the different parts of the article. They looked especially at plain wrong statements, if I named “all” the important frameworks / tools. They might not completely agree with the comparison to other language (after all, I wrote the article), but they helped me a lot to get things not too wrong:</p> <ul> <li><a href="https://www.linkedin.com/pub/s%C3%B6ren-liebich/31/b2a/252">Sören Liebich</a> (<a href="https://twitter.com/liebsoer">@liebsoer</a>) has several years of experience with Java web development and helped me to name the important tools / technologies used in the Java stack.</li> <li>Henning Dieterichs helped me to fix some of the mistakes in the C# part and reminded me of Hack and the positive sides of PHP.</li> <li>Stefan had a look at the PHP section.</li> </ul> <p>Thank you!</p> Increase the maximum file upload size in PHP //martin-thoma.com/increase-maximum-upload-size-in-php/ Sun, 07 Jun 2015 09:13:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/increase-maximum-upload-size-in-php <p>Create a <code>test.php</code> with the following content to check your current maximum upload size.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#369;font-weight:bold">phpinfo</span>(); <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>Search your <code>php.ini</code> in the Apache folder:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ find /etc -name 'php.ini' /etc/php5/cli/php.ini /etc/php5/apache2/php.ini </pre></div> </div> </div> <p>Edit it. Set <code>upload_max_filesize</code> and <code>post_max_size</code> to whatever you want.</p> <p>Restart the server with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo service apache2 restart </pre></div> </div> </div> 3D Photospheres //martin-thoma.com/optonaut/ Thu, 21 May 2015 16:23:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/optonaut <p>I’ve been to New York City a few months ago. It was an interesting experience. Everything is so big, it is difficult to get a feeling for it if you haven’t seen it yourself. For example, the <a href="https://en.wikipedia.org/wiki/National_September_11_Memorial_%26_Museum">WTC Memorial</a> is overwhelmingly large. I tried to capture that in a photograph with my Panasonic DMC-TZ41, but it just doesn’t look that large:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/NYC-Memorial-Pool-1.jpg"><img src="//martin-thoma.com/captions/NYC-Memorial-Pool-1.jpg" alt="WTC Memorial" width="500" height="375" class="" /></a><p class="wp-caption-text">WTC Memorial</p></div> <p>A photosphere captures that much better (it looks great on my Smartphone, but not nearly as well on the web): <a href="//martin-thoma.com/html5/photosphere-wtc-memorial">Android Photosphere</a></p> <p>Optonaut goes one step further. This app is able to create 3D photospheres.</p> <h2 id="how-it-works---user-perspective">How it works - User perspective</h2> <p>You start the app, slowly turn around yourself to capture everything around you. This includes your feet and the sky, if you really want a complete photosphere. The recording process the same as for Android Photospheres, but probably with a slightly different interface:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/optonaut-recording-process.gif"><img src="//martin-thoma.com/captions/optonaut-recording-process.gif" alt="Optograph recording process" width="500" height="333" class="" /></a><p class="wp-caption-text">Optograph recording process</p></div> <p>When you want to watch it in 3D you have to have something that holds it in front of your face at the right distance. Cardboard is an easy and cheap possibility to do so:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/optonaut-cardboard.jpg"><img src="//martin-thoma.com/captions/optonaut-cardboard.jpg" alt="Cardboard" width="500" height="750" class="" /></a><p class="wp-caption-text">Cardboard</p></div> <p>And, of course, you can already share optographs:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/sharing-optographs.jpg"><img src="//martin-thoma.com/captions/sharing-optographs.jpg" alt="Sharing Optographs" width="500" height="281" class="" /></a><p class="wp-caption-text">Sharing Optographs</p></div> <h2 id="how-it-works---developers-perspective">How it works - Developers perspective</h2> <p>Optonaut makes use of the camera and takes a lot of images. Those images are combined to a photosphere by a process called <a href="https://en.wikipedia.org/wiki/Image_stitching">image stitching</a>. This means you search points which seem to match to build one big image from many small images. A big problem is that your camera moves quite a lot in space and the environment changes. So there might not be any way to make a perfect match. Sensors like the compass and the <a href="https://en.wikipedia.org/wiki/Accelerometer">accelerometer</a> help to figure out at which direction you are currently pointing. Programs like <a href="http://hugin.sourceforge.net/">hugin</a> stitch images semi-automatically, but Optonaut works completely automatically.</p> <p>From my experience with Android Photospheres, this works much better when the objects around you are far away. That means it doesn’t work in your room.</p> <p>Then Optonaut uses a technique called <a href="https://en.wikipedia.org/wiki/Stereoscopy">stereoscopy</a>. They show you different images for each eye to give you the impression of a 3D image. They also use a different photosphere techique to “mix images dynamically”. Optonaut claims that this does work for close objects (in contrast to the traditional photosphere apps like Google Photosphere, Photosynth or Microsoft ICE).</p> <p>As they can figure out where you look at with the accelerometer / compass, they adjust the images accordingly for each eye to create a 3D impression:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/optograph.gif"><img src="//martin-thoma.com/captions/optograph.gif" alt="Stereographic images produced by Optonaut" width="500" height="248" class="" /></a><p class="wp-caption-text">Stereographic images produced by Optonaut</p></div> <p>Now it gets very interesting. Usually, you would need two cameras next to each other to take two slightly shifted images. But Optonaut needs only one camera. They make use of the fact that you rotate around your axis to photograph your environment. Optonaut takes two images which are next to each other, match them, deskew them. Et voilà: You are able to get a 3D impression!</p> <p>A side note: The 3D photosphere is stored as an archive of images.</p> <h2 id="the-optonaut-team">The Optonaut Team</h2> <p>Optonaut has two founders: Emanuel Jöbstl and Johannes Schickling. I’ve had the luck to work with them in my first hackathon (CODEFEST8). We won in Karlsruhe with an App / web service with a fully automatic drivers logbook (<a href="http://logbookapp.de/">logbookapp.de</a>). Both of them are great developers. Emanuel created the (working!) Android app which connected to the car within a couple of hours and Johannes made a beatiful frontend in the same time.</p> <p>Emanuel knows a lot about protocols, can understand mathematically complex algorithms and solve conceptually difficult problems. I guess he wrote the stitching algorithm.</p> <p>I’ve learned a lot from Johannes about tools. He is a perfectionist. In situations where most people would say “hey, it works, lets drink some coffee” he is still working hard to get the best user experience, making the code more maintainable by refactoring it, improving the way how code is built / deployed. In a short-term project this costs probably more time than doing it quick-and-dirty, but on the medium/long run (e.g. more than 2 weeks) it saves a lot of work.</p> <p>And Optonaut is such a long-term project. They are working on it for quite a while now, so I am sure the quality is pretty high. I am very curious if the <a href="https://www.kickstarter.com/projects/optonaut/optonaut-virtual-reality-photography">Kickstarter campaign</a> works as well as they hope and I cannot wait for the first people to share their optographs from amazing places!</p> <h2 id="future-of-optonaut">Future of Optonaut</h2> <p>The Optonaut team plans to build a sharing site where you can show others amazing places. They want to completely redesign the App.</p> <p>I guess the stitching algorithm is something where you can put endless effort in. It is an optimization problem where it is not completely clear what to optimize, so I guess this will continually be improved.</p> <h2 id="i-want-it-what-do-i-need">I want it! What do I need?</h2> <p>You need an Android / iOS smartphone. There seems to be a web-based viewer which works with Chrome/Firefox/Safari, too.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="http://optonaut.com/">Optonaut.com</a>: The official website <ul> <li><a href="http://demo.optonaut.com/">demo.optonaut.com</a>: In case you have a smartphone and a Cardboard, you can try the web demo already.</li> </ul> </li> <li><a href="https://www.kickstarter.com/projects/optonaut/optonaut-virtual-reality-photography">Kickstarter</a>: Support them, get early access / the App and your own Cardboard</li> </ul> Getting a Feeling for Energy //martin-thoma.com/get-a-feeling-for-energy/ Tue, 19 May 2015 19:17:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/get-a-feeling-for-energy <p>Have you heard of <a href="https://www.indiegogo.com/projects/gravitylight-made-in-africa/x/7191655#/story">GravityLight</a>?</p> <p>It is a gravity-powered lamp designed as an alternative for off-grid families who would otherwise use kersene lamps. It is basically only a 12kg weight, lifted and put on the gravity light. When the weight goes down again it pulls a cord. This cord makes an electric motor which generates electricity for LEDs. If you lift the weight 1.83m, the light lasts for about 20 minutes.</p> <p>I wondered how much weight I would need to lift (assuming 100% efficiency) to power my computer for 8 hours.</p> <p>According to the power supply unit, my laptop can consume up to 65 Watt. That is astonishingly low. I think my big one is at about 600-800 Watt.</p> <p>\begin{align} 65 W \cdot 8 h &amp;= \frac{65 kg \cdot m^2 \cdot 8h \cdot 60 \frac{min}{h} \cdot 60 \frac{s}{min}}{s^3}<br /> &amp;= 1872 \cdot 10^3 \frac{kg \cdot m^2}{s^2} \end{align}</p> <p>You might also remember from your physics courses that <a href="https://en.wikipedia.org/wiki/Potential_energy">potential energy</a> is <code>$E_{pot} = m \cdot g \cdot h$</code> where <code>$m$</code> is the mass (in kg), <code>$g = 9.80 \frac{m}{s^2}$</code> is the gravitational acceleration and <code>$h$</code> is the height in meters.</p> <p>\begin{align} m \cdot h &amp;= \frac{E_{pot}}{g}<br /> &amp;= \frac{1.872 \cdot 10^6 \frac{kg \cdot m^2}{s^2}}{9.80 \frac{m}{s^2}}<br /> &amp;= 191.0 \cdot 10^3 kg \cdot m \end{align}</p> <p>This means I would have to lift 191 000 packages one liter of milk to a height of 1 meter. Every day. Just to let my small laptop run.</p> <p>Or lets view it from another angle. I think lifting about 5 packages of milk to a height of about 1.8m each hour would not be too exhausting. This would generate about <code>$E_{pot} = 5kg \cdot 1.80m \cdot 9.80 \frac{m}{s^2} / (1h \cdot 60 \frac{min}{h} \cdot 60 \frac{s}{min}) = 0.0245 \frac{kg \cdot m^2}{s^3} = 0.0245 W$</code>. Lets think what you can power with 0.0245 Watt…</p> <p>It is amazing about how much energy we have today.</p> Python Markov Chain Packages //martin-thoma.com/python-markov-chain-packages/ Tue, 12 May 2015 20:45:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-markov-chain-packages <p>Markov Chains are probabilistic processes which depend only on the previous state and not on the complete history. One common example is a very simple weather model: Either it is a rainy day (R) or a sunny day (S). On sunny days you have a probability of 0.8 that the next day will be sunny, too. On rainy days you have a probability of 0.6 that the next day will be rainy, too. As you have only two possible weather conditions, the probability that it changes from sunny do rainy is 0.2 and vice versa it is 0.4.</p> <p>You can visualize this with a graph like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/markov-chain-rain-sun.png"><img src="//martin-thoma.com/captions/markov-chain-rain-sun.png" alt="Simple Markov chain weather model" width="500" height="237" class="" /></a><p class="wp-caption-text">Simple Markov chain weather model</p></div> <p>I am taking a course about markov chains this semester. Today, we’ve learned a bit how to use R (a programming language) to do very basic tasks.</p> <h2 id="r-vs-python">R vs Python</h2> <p>The following will show some R code and then some Python code for the same basic tasks. As an example, I’ll use reproduction. The states are <code>$S_1 = \{AA, AA\}$</code>, <code>$S_2 = \{AA, Aa\}$</code>, <code>$S_3 = \{AA, aa\}$</code>, <code>$S_4=\{Aa,Aa\}$</code>, <code>$S_5 = \{Aa, aa\}$</code> and <code>$S_6 = \{aa, aa\}$</code>.</p> <p>The idea is that each pair of parents give birth to two children. The parents <code>$S_2 = \{AA, Aa\}$</code> can give birth to {{AA, AA}, {AA, Aa}, {Aa, Aa}}. This results in the following state transition matrix.</p> <p><code>$\begin{pmatrix}1 &amp; 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0 \\ 1/4 &amp; 1/2 &amp; 0 &amp; 1/4 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0\\ 1/16 &amp; 1/4 &amp; 1/8 &amp; 1/4 &amp; 1/4 &amp; 1/16\\ 0 &amp; 0 &amp; 0 &amp; 1/4 &amp; 1/2 &amp; 1/4\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0 &amp; 1\end{pmatrix}$</code></p> <p>The rows mean from which state you start, the colums are the states you can get to.</p> <p>Now, how would you define this matrix with R?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>P = matrix(c(1,0,0,0,0,0, 1/4,1/2,0,1/4,0,0, 0,0,0,1,0,0, 1/16, 1/4, 1/8, 1/4, 1/4, 1/16, 0,0,0, 1/4, 1/2, 1/4, 0,0,0,0,0,1), byrow=TRUE, nrow=6) </pre></div> </div> </div> <p>And this is how you do it with Python: You first need to <a href="http://docs.scipy.org/doc/numpy/user/install.html">install numpy</a>. This is very easy with Linux (<code>sudo apt-get install python-numpy</code>), but I’ve heard it is not that easy with Windows systems.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">as</span> np P = np.matrix([[<span style="color:#60E">1.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>], [<span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">2</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>], [<span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>], [<span style="color:#60E">1.</span>/<span style="color:#00D">16</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">8</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">16</span>], [<span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">2</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>], [<span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>]]) </pre></div> </div> </div> <p>A common matrix operation is taking the <code>$n$</code>-th power. This is how you do it with R: First, install the library “expm” by executing <code>install.packages("expm")</code>. Then</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>library(&quot;expm&quot;) n = 5 Pn = P%^%n </pre></div> </div> </div> <p>and this is the Python way:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>n = <span style="color:#00D">5</span> Pn = P**n </pre></div> </div> </div> <p>Visualizing data is a very important tool. For example, we want to know the probabilities for the current state for the next 20 steps when you started in <code>$S_3$</code>.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>library(&quot;expm&quot;) P = matrix(c(1,0,0,0,0,0, 1/4,1/2,0,1/4,0,0, 0,0,0,1,0,0, 1/16, 1/4, 1/8, 1/4, 1/4, 1/16, 0,0,0, 1/4, 1/2, 1/4, 0,0,0,0,0,1), byrow=TRUE, nrow=6) v = c(0,0,1,0,0,0) for (step in 1:20) { matplot(t(sapply(1:20, function (step) {v %*% (P %^% step)})), cex=0.7, ylab=&quot;&quot;) } </pre></div> </div> </div> <p>This gives the following plot:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/reproductin-rplot.png"><img src="//martin-thoma.com/captions/reproductin-rplot.png" alt="State probabilities starting in S3 after 1..20 steps (plotted with R)" width="500" height="384" class="" /></a><p class="wp-caption-text">State probabilities starting in S3 after 1..20 steps (plotted with R)</p></div> <p>The Python equivalent is</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">as</span> np <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">matplotlib</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">pyplot</span> P = np.matrix([[<span style="color:#60E">1.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>], [<span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">2</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>], [<span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>], [<span style="color:#60E">1.</span>/<span style="color:#00D">16</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">8</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">16</span>], [<span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">2</span>, <span style="color:#60E">1.</span>/<span style="color:#00D">4</span>], [<span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">0.</span>, <span style="color:#60E">1.</span>]]) v = np.matrix([[<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">1</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>]]) <span style="color:#777"># Get the data</span> plot_data = [] <span style="color:#080;font-weight:bold">for</span> step <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">20</span>): result = v * P**step plot_data.append(np.array(result).flatten()) <span style="color:#777"># Convert the data format</span> plot_data = np.array(plot_data) <span style="color:#777"># Create the plot</span> pyplot.figure(<span style="color:#00D">1</span>) pyplot.xlabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Steps</span><span style="color:#710">'</span></span>) pyplot.ylabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Probability</span><span style="color:#710">'</span></span>) lines = [] <span style="color:#080;font-weight:bold">for</span> i, shape <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">zip</span>(<span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">6</span>), [<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">h</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">H</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">s</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">8</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">r+</span><span style="color:#710">'</span></span>]): line, = pyplot.plot(plot_data[:, i], shape, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">S%i</span><span style="color:#710">&quot;</span></span> % (i+<span style="color:#00D">1</span>)) lines.append(line) pyplot.legend(handles=lines, loc=<span style="color:#00D">1</span>) pyplot.show() </pre></div> </div> </div> <p>The result looks like this</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/05/reproductin-python-plot.png"><img src="//martin-thoma.com/captions/reproductin-python-plot.png" alt="State probabilities starting in S3 after 1..20 steps (plotted with Python)" width="500" height="356" class="" /></a><p class="wp-caption-text">State probabilities starting in S3 after 1..20 steps (plotted with Python)</p></div> <p>I’ve played around with the <a href="http://matplotlib.org/api/markers_api.html">matplotlib markers</a> to make sure all points are visible.</p> <h2 id="python-markov-packages">Python Markov Packages</h2> <p>There seem to be quite a few Python Markov chain packages:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pip search markov PyMarkovChain - Simple markov chain implementation autocomplete - tiny 'autocomplete' tool using a &quot;hidden markov model&quot; cobe - Markov chain based text generator library and chatbot twitter_markov - Create markov chain (&quot;_ebooks&quot;) accounts on Twitter markovgen - Another text generator based on Markov chains. pyEMMA - EMMA: Emma's Markov Model Algorithms pymc - Markov Chain Monte Carlo sampling toolkit. hmmus - Posterior decoding with a hidden Markov model marbl-python - A Python implementation of the Marbl specification for normalized representations of Markov blankets in Bayesian networks. pymdptoolbox - Markov Decision Process (MDP) Toolbox gibi - Generate random words based on Markov chains markovgenerator - Markov text generator pythonic-porin - Nanopore Data Analysis package. Provides tools for reading data, performing event detection, segmentation, visualization, and analysis using hidden Markov models, and other tools. Designed for the UCSC Nanopore Group. PyMarkovTextGenerator - Random text generator base on Markov chains. MCREPOGEN - Markov Chain Repository Generator vokram - A toy Markov chain implementation. MarkovEquClasses - Algorithms for exploring Markov equivalence classes: MCMC, size counting hmmlearn - Hidden Markov Models in Python with scikit-learn like API twarkov - Markov generator built for generating Tweets from timelines MCL_Markov_Cluster - Markov Cluster algorithm implementation pyborg - Markov chain bot for irc which generates replies to messages pydodo - Markov chain generator mwordgen - MWordGen is a Markov statistics based word generator. Markov - Python library for Hidden Markov Models markovify - Use Markov chains to generate random semi-plausible sentences based on an existing text. treehmm - Variational Inference for tree-structured Hidden-Markov Models PyMarkov - Markov Chains made easy </pre></div> </div> </div> <p>However, most of them are for hidden markov model training / evaluation. There seems to be no package which can visualize markov chains just by taking the state transition matrix.</p> <p>There seems also not to be any package which makes it easy to classify states as transient / recurrent, get the absorption time, …</p> <p>If somebody is interested in that, we could make a little project for it ☺</p> <h3 id="pymarkovchain">PyMarkovChain</h3> <p>Source is on <a href="https://github.com/TehMillhouse/PyMarkovChain">github.com/TehMillhouse/PyMarkovChain</a>. It is less than 150 lines of code and probably no functionality.</p> <p>I asked the author to remove the package from PyPI (see <a href="https://github.com/TehMillhouse/PyMarkovChain/issues/13">issue #13</a>).</p> <h3 id="pyemma">pyEMMA</h3> <p>I’ve found the <a href="http://www.pythonhosted.org/pyEMMA/">documentation</a> and the <a href="https://pypi.python.org/pypi/pyEMMA">project on PyPI</a>. The source is on <a href="https://github.com/markovmodel/PyEMMA">github.com/markovmodel/PyEMMA</a>.</p> <h3 id="markovequclasses">MarkovEquClasses</h3> <p><a href="https://pypi.python.org/pypi/MarkovEquClasses/1.0">PyPI</a></p> <h3 id="pymarkov">PyMarkov</h3> <p>It is only about 100 lines of very simple code. It seems to be another random sentence generator. See <a href="https://pypi.python.org/pypi/PyMarkov">PyPI</a>.</p> <h3 id="hidden-markov-models">Hidden Markov Models</h3> <p>The following might be interesting, but I didn’t take a close look at them because I was looking for “normal” markov models:</p> <ul> <li>hmmus</li> <li>hmmlearn</li> <li>Markov</li> <li>treehmm</li> </ul> <p>There are also quite a few other modules which seem to generate data with markov chains.</p> <h2 id="todo">TODO</h2> <ul> <li>http://www.ncbi.nlm.nih.gov/pmc/articles/PMC3097064/</li> <li>https://pymc-devs.github.io/pymc/README.html</li> <li>https://github.com/riccardoscalco/Pykov</li> </ul> Machine Learning 2 //martin-thoma.com/machine-learning-2-course/ Mon, 11 May 2015 11:00:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/machine-learning-2-course <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Machine Learning 2&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://tks.anthropomatik.kit.edu/21_52.php">Herrn Prof. Dr. Marius Zöllner</a> im Sommersemester&nbsp;2015 gehört. <br />Es gibt auch einen Artikel zu <a href="http://martin-thoma.com/machine-learning-1-course/">Machine Learning 1</a></div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="einfhrung">Einführung</h3> <p>Slides: <a href="https://ilias.studium.kit.edu/ilias.php?ref_id=429607&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI"><code>01_Einfu__hrung_MLII.pdf</code></a></p> <p>Rückblick auf <a href="//martin-thoma.com/machine-learning-1-course/">ML 1</a>. MLNN steht übrigens für <i>Multi-Layer Neural Network</i>.</p> <h3 id="semi-supervised-learning">Semi-Supervised Learning</h3> <p>Slides: <a href="https://ilias.studium.kit.edu/ilias.php?ref_id=432731&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI"><code>02_Semi-supervised-learning.pdf</code></a></p> <dl> <dt><dfn>Überwachtes Lernen</dfn> (engl. <dfn>Supervised Learning</dfn>)</dt> <dd>Alle Trainingsdaten liegen mit Labels vor.</dd> <dt><dfn>Unüberwachtes Lernen</dfn> (engl. <dfn>Unsupervised Learning</dfn>)</dt> <dd>Alle Trainingsdaten liegen ohne Labels vor.</dd> <dt><a href="https://en.wikipedia.org/wiki/Semi-supervised_learning"><dfn>Semi-Supervised Learning</dfn></a> (<dfn>SSL</dfn>)</dt> <dd>Die meisten Trainingsdaten liegen ohne Labels vor, jedoch gibt es für jede Klasse auch gelabelte Daten.</dd> <dt><dfn>Self-Learning</dfn> (<dfn>Self-Training</dfn>, <dfn>Self-Labeling</dfn>, <dfn>Decision-directed learning</dfn>)</dt> <dd><i>Self-Training</i> ist ein Algorithmus zum Semi-supervised Learning. Er geht wie folgt vor: <ol> <li>Trainiere mit gelabelten Daten.</li> <li>Werte ungelabelte Daten aus.</li> <li>Füge Daten, bei denen sich der Klassifizierer sicher ist, zu den Trainingsdaten hinzu.</li> <li>Zurück zu Schritt&nbsp;1.</li> </ol> Dabei sind folgende Variationen vorstellbar: <ul> <li>Füge alle Daten hinzu.</li> <li>Füge nur Daten hinzu, bei denen sich der Klassifizierer sicher ist.</li> <li>Gewichte Daten mit der Sicherheit.</li> </ul> </dd> <dt><dfn>Co-Training</dfn> (<dfn>Mit-Lernen</dfn>)</dt> <dd><i>Co-Training</i> ist ein Algorithmus zum Semi-supervised Learning. Er geht wie folgt vor: <ol> <li>Splitte jeden Feature-Vektor auf die gleiche Art in zwei Feature-Vektoren mit disjunkten Features auf.</li> <li>Trainiere zwei unterschiedliche Klassifizierer auf den beiden unterschiedlichen Feature-Mengen der gelabelten Daten.</li> <li>Label mit den beiden Klassifizieren die ungelabelten Daten.</li> <li>Füge ungelabelte Daten dem Trainingsdatensatz (also den gelabelten Daten) hinzu, falls die Klassifizierer für diese eine hohe Konfidenz aufweisen.</li> <li>Zurück zu Schritt&nbsp;2.</li> </ol> Dabei sind folgende Variationen vorstellbar: <ul> <li>Demokratisches Voting: Bei mehr als 2&nbsp;Klassifizierern.</li> <li>Schwellwert: Nur hinzufügen, wenn alle Klassifizierer jeweils eine Schwelle überschreiten.</li> <li>Gewichtes Voting: Alle Klassifizierer zusammen müssen eine Schwelle überschreiten.</li> </ul> </dd> <dt><dfn>Low Density Separation</dfn></dt> <dd>Methoden, welche Low Density separation benutze versuchen die Entscheidungsgrenze in eine Region niedriger Dichte zu legen. Ein Beispiel ist die <i>Transductive SVM</i>.</dd> </dl> <p>Weiteres:</p> <p>Hier könnte ich mir gut vorstellen, dass man eine Bachelor / Master-Arbeit macht. Man könnte sich große gelabelte Datensätze suchen, einen gewissen Teil der Labels weglassen (also einige Trainingsdaten als “ungelabelt” behandeln) und die verschiedenen <abbr title="Semi-Supervised Learning">SSL</abbr>-Methoden untersuchen. Bis zu 20% gelabelte Daten hoch wäre es interessant; also z.B. (0.5%, 1%, 2%, 3%, 5%, 10%, 15%, 20% gelabelte Daten). Mit mehr gelabelten Daten könnte man argumentieren, dass man es sich vermutlich leisten könnte auch den Rest noch zu labeln. Siehe Folie 28-31.</p> <h3 id="ssl-and-active-learning">SSL and Active Learning</h3> <p>Slides: <code>03_Semi-supervised+Active-learning.pdf</code></p> <dl> <dt><a href="https://de.wikipedia.org/wiki/Lagrange-Multiplikator"><dfn>Lagrange-Multiplikator</dfn></a></dt> <dd>Lagrange-Multiplikatoren sind ein Verfahren der Optimierungstheorie. Sie werden genutzt, wenn ein Optimierungsproblem mit Nebenbedingungen vorliegt. Durch sie kann die Nebenbedingung eliminiert werden.</dd> <dt><dfn>Active Learning</dfn></dt> <dd>Die Lernmaschine wählt die zu lernenden Daten selbst aus.</dd> <dt><dfn>Query Synthesis</dfn> (siehe <a href="http://burrsettles.com/pub/settles.activelearning.pdf">Active Learning Literature Survey</a>)</dt> <dd>Der Lerner kann Feature-Vektoren (Querys) <a href="https://en.wikipedia.org/wiki/De_novo">de novo</a>, also von Grund auf neu / selbst erzeugen. Er kann für diesen neuen Query ein Orakel befragen, was das Label ist.</dd> <dt><dfn>Selective Sampling</dfn> (Selektive Entnahme, siehe <a href="http://dl.acm.org/citation.cfm?id=2503327">Selective sampling and active learning from single and multiple teachers</a>)</dt> <dd>Selective Sampling ist eine Methode des aktiven Lernens. Dabei wird jede Runde \(t\) dem Lerner ein Feature-Vektor \(x_t \in \mathbb{R}^n\) präsentiert. Der Lerner muss sich jede Runde entscheiden, ob er einen Preis bezahlt um das Label zu sehen. Der Lerner hat also zwei Ziele, die miteinander in Konflikt stehen: Er will alles richtig klassifizieren, aber zugleich die Kosten so niedrig wie möglich halten.</dd> <dt><dfn>Pool-Based Active Learning</dfn></dt> <dd>Pool-Based Active Learning ist eine Methode des aktiven Lernens. Dabei wird von einem Pool an ungelabelten Daten \(\mathcal{U}\) ausgegangen und einem deutlich kleineren Pool \(\mathcal{L}\) an gelabelten Daten. Queries werden aus \(\mathcal{U}\) gezogen. Dabei wird ganz \(\mathcal{U}\) evaluiert und für den hilfreichsten Feature-Vektor \(x \in \mathcal{U}\) nach einem Label gefragt.</dd> <dt><dfn>Hinge-Funktion</dfn></dt> <dd>\[f(x) = \max(x, 0)\]</dd> <dt>Query-by-Committee (<dfn>QBC</dfn>)</dt> <dd>Es wird ein Committee \(\mathcal{C}\) an Klassifikatoren trainiert, welches gemeinsam (z.B. durch majority vote) eine Klassifikation trifft. Allgemeiner Ansatz: <ul> <li>Trainiere eine Menge \(\mathcal{C}\) an Klassifikatoren</li> <li>Wähle neue Daten, wenn die Hypothesen Wiedersprüchlich sind</li> </ul> Selektive Entnahme: <ol> <li>Beobachte neue Instanz \(x\) und werte diese mit \(\mathcal{C}\) aus</li> <li>Frage das Label ab, falls es einen Wiederspruch in den Hypothesen von \(\mathcal{C}\) für \(x\) gibt.</li> <li>Neu trainiren, zurück zu 1</li> </ol> Pool-based Active Learning: <ol> <li>Messung des Wiederspruchs der Hypothesen für alle Instanzen \(x\)</li> <li>Ranking (z.B. Entropie)</li> <li>Abfrage der Labels für die \(k\) widersprüchlichsten Instanzen</li> <li>Neu trainiren, zurück zu 1</li> </ol> </dd> </dl> <p>Weiteres:</p> <ul> <li>Ausreißerproblem: Ausreißer sollten im QBC nicht genommen werden. Dazu könnte die Dichte im Datenraum gemessen werden.</li> </ul> <h3 id="reinforcement-learning">Reinforcement Learning</h3> <p>Slides: <code>04_Reinforcement_Learning_II.pdf</code></p> <p>Siehe auch:</p> <ul> <li><a href="https://martin-thoma.com/neuronale-netze-vorlesung/#tocAnchor-1-1-9">Neuronale Netze</a></li> <li><a href="https://martin-thoma.com/machine-learning-1-course/#tocAnchor-1-1-4">Machine Learning 1</a></li> <li><a href="https://github.com/MartinThoma/cat-vs-mouse">Cat vs. Mouse code</a></li> <li>Berkeley <ul> <li>CS188 Intro to AI: <a href="http://ai.berkeley.edu/reinforcement.html">Project 3: Reinforcement Learning</a></li> <li>Dan Klein, Pieter Abbeel: <a href="https://www.youtube.com/watch?v=w33Lplx49_A">Lecture 10: Reinforcement Learning</a> on YouTube. University of California, Berkeley. This expalins TD-learning.</li> </ul> </li> </ul> <dl> <dt><a href="https://de.wikipedia.org/wiki/Markow-Entscheidungsproblem"><dfn>Markov Decision Process</dfn></a> (<dfn>MDP</dfn>)</dt> <dd>Ein Markovscher Entscheidungsprozess ist ein 5-Tupel \((S, A, T, r, p_0)\), wobei <ul> <li>\(S\) eine endliche Zustandsmenge,</li> <li>\(A\) eine endliche Menge von Aktionen,</li> <li>\(T_a(s, s') = T(s_{t+1}=s'|s_t = s, a_t = a)\) die Wahrscheinlichkeit zu einem beliebigen Zeitpunkt von Zustand \(s\) mit der Aktion \(a\) in den Zustand \(a'\) zu kommen (engl. Transition),</li> <li>\(r_a(s, s')\) ist die Belohnung (Reward), die man direkt erhält wenn man erhält wenn man von Zustand \(s\) mit Aktion \(a\) in Zustand \(s'\) kommt,</li> <li>\(p_0\) ist die Startverteilung auf die Zustände \(S\)</li> </ul> </dd> <dt><dfn>Partially observable Markov decision process</dfn> (<dfn>POMDP</dfn>)<a name="pomdp-definition"></a></dt> <dd>Ein <i>partially observable Markov decision process</i> ist ein 7-tupel <span>\(S, A, T, R, \Omega, O, \gamma\)</span>, wobei <ul> <li>\(S\) die Zustandsmenge,</li> <li>\(A\) die Aktionsmenge,</li> <li>\(T: S \times A \times S \rightarrow \mathbb{R}\) die probabilisitische Zustandsübergangsfunktion (transition function) ist,</li> <li>\(R: S \times A \rightarrow \mathbb{R}\) die Reward-Funktion,</li> <li>\(\Omega\) die Menge der möglichen Beobachtungen,</li> <li>\(O\) die Wahrscheinlichkeit der Beobachtungen, gegeben ein Zustand und eine Aktion und</li> <li>\(\gamma \in [0, 1]\) der Diskontierungsfaktor</li> </ul> ist. </dd> <dt><dfn>Options</dfn></dt> <dd>Eine <i>Option</i> ist wohl-definiertes Verhalten, welches im hierarchischen <abbr title="Reinforcement Learning">RL</abbr> eingesetzt werden kann. Es ist ein Baustein für komplexe Pläne. Options werden in Semi-MDPs eingesetzt und ersetzen dort die Aktionen.</dd> <dt><dfn>Hierarchien Abstrakter Maschinen</dfn> (<dfn>HAM</dfn>)</dt> <dd>Ein <abbr title="Markov Decision Process">MDP</abbr> wird mit Maschinen \(\{M_i\}\) kombiniert. Jede Maschine repräsentiert einen Teil der Policy. Jede Maschine verwendet eigene Zustände \(m_t^i\) und globale Zustände \(s_t\). Maschinen werden durch Zustandsautomaten abgebildet.</dd> <dt><dfn>MaxQ-Dekomposition</dfn> (siehe [<a href="#ref-die00" name="ref-die00-anchor">Die00</a>])</dt> <dd>Das zu lösende MDP \(M\) wird als Menge von Unteraufgaben \(\{M_0, \dots, M_n\}\) interpretiert. Dabei ist \(M_0\) das Haupt-MDP. TODO.</dd> </dl> <p>Folie 35:</p> <ul> <li>NODO: Was heißt hier “mit festen Knoten”?</li> </ul> <h3 id="a-namedynamic-bayes-networksadynamische-bayessche-netze"><a name="dynamic-bayes-networks"></a>Dynamische Bayessche Netze</h3> <p>Slides: <code>05_DynamischeBayesscheNetze.pdf</code></p> <dl> <dt><a href="https://de.wikipedia.org/wiki/Bedingte_Wahrscheinlichkeit#Multiplikationssatz"><dfn>Multiplikationssatz</dfn></a></dt> <dd>Seien \(A, B, X_i\) Ereignisse. Dann gilt: \[P(X_1, \dots, X_n) = P(X_1) \cdot \prod_{k=2}^n P(X_k | X_{k-1}, \dots, X_1)\] und insbesondere \[P(A\cap B) = P(A, B) = P(A\mid B) \cdot P(B)\]</dd> <dt><a href="https://de.wikipedia.org/wiki/Bedingte_Wahrscheinlichkeit#Gesetz_der_totalen_Wahrscheinlichkeit"><dfn>Gesetz der totalen Wahrscheinlichkeit</dfn></a></dt> <dd>Seien \(A_1, \dots, A_n\) paarweise disjunkte Ereignisse mit \(A = \sum_{i=1}^n A_i\). Dann gilt für jedes beliebige Ereignis \(B\): \[P(B) = \sum_{i=1}^n P(B | A_i) \cdot P(A_i) = P(A_i, B)\]</dd> <dt><a href="https://de.wikipedia.org/wiki/Satz_von_Bayes"><dfn>Satz von Bayes</dfn></a></dt> <dd>Seinen \(A, B\) Ereignisse mit \(P(B) &gt; 0\). Dann gilt \[P(A|B) = \frac{P(B|A) \cdot P(A)}{P(B)}\] Hierbei heißt \(P(A|B)\) die <i>a posteriori Wahrscheinlichkeit</i>, \(P(B|A)\) die <i>likelihood</i>, \(P(A)\) die <i>a priori Verteilung über \(A\)</i> und \(P(B)\) die <i>a priori Verteilung über \(B\)</i>.</dd> <dt><a href="https://de.wikipedia.org/wiki/Bayessches_Netz"><dfn>Bayessches Netz</dfn></a> (Siehe <a href="https://www.youtube.com/watch?v=VfyxPtlqZh4">Lecture 13: Bayes Nets</a>)</dt> <dd>Ein <i>Bayessches Netz</i> ist ein <abbr title="Directed Acyclical Graph">DAG</abbr>, bei dem die Knoten Zufallsvariablen und die Kanten bedingte Abhängigkeiten beschreiben. Bayessche Netze sind zur Modellierung kausaler Zusammenhänge geeignet.</dd> <dt><a href="https://de.wikipedia.org/wiki/Markov_Random_Field"><dfn>Markov Random Field</dfn></a></dt> <dd>Siehe <a href="https://martin-thoma.com/machine-learning-1-course/#mrf-definition">ML 1</a></dd> <dt><a href="https://en.wikipedia.org/wiki/Dynamic_Bayesian_network"><dfn>Dynamisches Bayessches Netz</dfn></a></dt> <dd><i>Dynamische Bayessche Netze</i> sind Bayessche Netze zur Beschreibung dynamischer Prozesse.</dd> <dt><a href="https://en.wikipedia.org/wiki/Markov_blanket"><dfn>Markov Blanket</dfn></a></dt> <dd>Sei \(G=(V,E)\) ein DAG zu einem Bayesschen Netz und \(v_S \in V\). Dann ist der Markov Blanket die folgende Knotenmenge \(B \subseteq V \setminus \{v_S\}\): <ul> <li>Die Elternknoten von \(v_S\) sind in \(B\).</li> <li>Die Kindknoten \(K = \{v_{K_1}, \dots, v_{K_n}\}\) sind in \(B\)</li> <li>Die Elternknoten von \(K\), ausgenommen von \(v_S\), sind in \(B\)</li> </ul> Diese Knotenmenge macht \(v_S\) unabhängig von anderen Knoten.</dd> <dt><a href="https://en.wikipedia.org/wiki/Naive_Bayes_spam_filtering"><dfn>Naive Bayes Spam Filter</dfn></a></dt> <dd>Ein naiver Bayes Spamfilter nutzt häufig Bag-of-Words Features. Man berechnet die Wahrscheinlichkeit, dass eine gegebene E-Mail Spam ist. Dazu geht man davon aus, dass die Wörter in einer E-Mail unabhängig von einander sind und nutzt den Satz von Bayes. Siehe <a href="https://de.wikipedia.org/wiki/Bayes-Klassifikator#Beispiel">Bayes-Klassifikator</a> für eine detailiertere Beschreibung.</dd> <dt><dfn>Bayes Filter</dfn></dt> <dd>Ein Bayes Filter ist eine Familie von Zufallsvariablen. Das könnte z.B. die \((x,y,z)\) Position eines GPS-Sensors sein. Diese Position ist verrauscht. Nun gibt es drei mögliche Anfragen: <ul> <li><b>Filtern</b>: Es liegen Messungen \(Z_0, \dots, Z_t\) vor, sage die aktuelle Position \(X_t\) vorher. Also <i>filtere das Rauschen</i> aus \(Z_t\) unter berücksichtigung, dass wir uns noch nicht teleportieren können: \[P(X_t | Z_t, \dots, Z_0)\]</li> <li><b>Prädizieren</b>: Es liegen Messungen \(Z_0, \dots, Z_t\) vor, sage die Position \(X_{t+k}\) vorher: \[P(X_{t+k} | Z_t, \dots, Z_0)\]</li> <li><b>Glätten</b>: Es liegen Messungen \(Z_0, \dots, Z_t\) vor, sage die Position \(P(X_{t-k} | Z_t, \dots, Z_0)\) vorher.</li> </ul> Beispiele für Bayes-Filter sind <ul> <li>Kalman-Filter</li> <li><abbr title="Hidden Markov Model">HMM</abbr></li> <li>Partikel Filter</li> </ul> </dd> <dt><dfn>Naiver Bayes'scher Spam Filter</dfn></dt> <dd>Ein probabilistischer Klassifikator welcher die Unabhängigkeit der Features vorraussetzt wird <i>naiv</i> genannt.<br /> <br /> Der naive bayessche Spam Filter nutzt Bayes Theorem um die Wahrscheinlichkeit zu berechnen, dass eine E-Mail Spam ist. </dd> <dt><a href="https://de.wikipedia.org/wiki/Kalman-Filter"><dfn>Kalman-Filter</dfn></a> (siehe <a href="http://arxiv.org/abs/1204.0375">Python-Implementierung</a>)</dt> <dd>Der Kalman-Filter ist ein Bayes-Filter. Er wird z.B. zum Schätzen einer Fahrzeugtrajektorie eingesetzt. Der Kalman-Filter besteht aus zwei Schritten: <ul> <li><b>Predict</b> the next step of the system given the previous measurements.</li> <li><b>Update</b> the estimate of the current state given the measurement of this time step.</li> </ul> </dd> <dt><dfn>Expectation Maximizaion Algorithm</dfn> (<dfn>EM-Algorithmus</dfn>)</dt> <dd> Der EM-Algorithmus kann als ein Clusteringalgorithmus mit weicher Clusterzugehörigkeit gesehen werden. Er findet die Parameter für gegebene Verteilungen (üblicherweise multivariate Normalverteilungen). Er löst das Henne-Ei Problem <ul> <li>Wenn man weiß wie genau die Wahrscheinlichkeitsverteilungen der Cluster parametrisiert sind ist es leicht die Daten den Clustern zuzuordnen.</li> <li>Wenn man die Daten einem Cluster zuordnen kann, dann ist es leicht die Parameter der Wahrscheinlichkeitsverteilung zu schätzen.</li> </ul> Wenn man sowohl Clusterzugehörigkeit als auch die Parameter der Verteilung schätzen muss ist es schwer. Man kann "zufällig" die initialen Parameter wählen, dann die Zuordnung machen. Der EM-Algorithmus iteriert also: <ul> <li><b>Expectation</b>: Weise alle Datenpunkte ihrem Cluster zu.</li> <li><b>Maximization</b>: Berechne die Parameter der Cluster neu.</li> </ul> Siehe <a href="https://www.youtube.com/watch?v=REypj2sy_5U">Mixture Models 1: the EM algorithm</a> </dd> </dl> <p>Typische Fragestellungen:</p> <ul> <li>Gegeben ist die Struktur eines Bayesschen Netzes: Wie lautet die Verteilung? <ul> <li>Dies wird üblicherweise mit dem <abbr title="Expectation Maximimization">EM</abbr>-Algorithmus gelöst.</li> </ul> </li> </ul> <p>Anwendungsfälle:</p> <ul> <li>Automatische Diagnose, gegeben die Symptome (Bayessches Netz)</li> <li>Fahrzeugverfolgung: Vorhersage von Routen, welche die Fahrzeuge nehmen werden (Dynamisches Bayessches Netz)</li> </ul> <p>Anmerkungen: Die Folien sind hier sehr gut! Insbesondere Folie 14-23 sollte man sich ansehen.</p> <p>Es scheint folgende Beziehung zu gelten: HMMs, Kalman-Filter, Extended Kalman-Filter, Partikel Filter sind Beispiele für Bayes-Filter. Bayes-Filter sind Beispiele für dynamische Bayessche Netze.</p> <p>Siehe auch:</p> <ul> <li>Udacity: <a href="https://www.youtube.com/watch?v=8O9GV4SUToA&amp;index=77&amp;list=PLAwxTw4SYaPkCSYXw6-a_aAoXVKLDwnHK">Artificial Intelligence for Robotics</a> - good content for Kalman Filters</li> </ul> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2016/01/tracking-robots.png" class="image"><img src="//martin-thoma.com/captions/tracking-robots.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Tracking Robots</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2016/01/probabilisitc-graphical-models.png" class="image"><img src="//martin-thoma.com/captions/probabilisitc-graphical-models.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Probabilistic Graphical Models</div></div></li></ul> <h3 id="probablistisch-relationale-modelle">Probablistisch Relationale Modelle</h3> <p>Slides: <code>06_Probablistisch_Relationale_Modelle.pdf</code></p> <p>Siehe auch:</p> <ul> <li>C. Howard and M. Stumptner and others. Model Construction Algorithms for Object-Oriented Probabilistic Relational Models. FLAIRS Conference, 2006.</li> <li>C. Howard and M. Stumptner. <a href="http://ieeexplore.ieee.org/xpl/login.jsp?arnumber=1592031">Situation assessments using object oriented probabilistic relational models</a>, in 8th International Conference on Information Fusion, 2005, vol.2. doi: 10.1109/ICIF.2005.1592031</li> </ul> <dl> <dt><dfn>Objektorientierte Probablistisch Relationales Modelle</dfn> (<dfn>OPRM</dfn>)</dt> <dd>Ein OPRM besteht nach [<a href="#ref-schu15" name="ref-schu15-anchor">Schu15</a>] aus <ul> <li>Eine Klassenmenge \(\mathbf{C} = \{C_1, \dots, C_n\}\),</li> <li>einer partiellen Ordnung über C, welche die Klassenhierarchie definiert,</li> <li>einer Menge einfacher, nicht probabilisitscher Attribute \(\Lambda_C = \{\lambda_1, \dots, \lambda_n \forall C \in \mathbf{C}\}\),</li> <li>einer Menge beschreibender Attribute \(\Delta_C = \{\delta_1, \dots, \delta_n\} \forall C \in \mathbf{C}\),</li> <li>einer Menge komplexer Attribute \(\Phi_C = \{\phi_1, \dots, \phi_n\} \forall C \in \mathbf{C}\). Die komplexen Attribute beschreiben funktionale Beziehungen zwischen Klassen.</li> </ul> Dieses Modell wurde in <a href="https://staff.fnwi.uva.nl/j.m.mooij/libDAI/">libDAI</a> umgesetzt. </dd> </dl> <h3 id="gaussche-prozesse">Gaussche Prozesse</h3> <p>Slides: <code>07_Gaussche_Prozesse.pdf</code></p> <p>I suggest reading the first two chapters of the online book <a href="http://www.gaussianprocess.org/">gaussianprocess.org</a> before starting to read the slides.</p> <p>See also:</p> <ul> <li><a href="https://martin-thoma.com/function-approximation/">Function Approximation</a></li> <li>The Talking Machines: <a href="http://www.thetalkingmachines.com/blog/2016/1/28/openai-and-gaussian-processes">OpenAI and Gaussian Processes</a></li> </ul> <dl> <dt><a href="https://de.wikipedia.org/wiki/Lineare_Regression"><dfn>Lineare Regression</dfn></a></dt> <dd>Die lineare Regression ist ein Modell zur approximation von Datenpunkten \((x, y) \in \mathbb{R}^n \times \mathbb{R}\) durch eine lineare Funktion, d.h. einer Funktion der Form \(f(x) = x^T \cdot w\). Dabei ist \(w \in \mathbb{R}^n\).<br /> <br /> Wenn man als Optimierungskriterium den quadratischen Abstand \[E(f, data) = \sum_{(x,y) \in data} (f(x) - y)^2\] nimmt, dann ist eine optimale Lösung durch \[w = (X^T X)^{-1} X^T y\] gegeben.<br /> <br /> Siehe auch: <a href="http://math.stackexchange.com/q/691812/6876">Proof of when is \(A=X^T X\) invertible?</a> sowie <a href="http://math.stackexchange.com/q/1626052/6876">Does a transformation + linear regression give the same regression as fitting a quadratic function?</a> </dd> <dt><dfn>Affine Regression</dfn></dt> <dd>Die affine Regression ist ein Modell zur approximation von Datenpunkten \((x, y) \in \mathbb{R}^n \times \mathbb{R}\) durch eine affine Funktion, d.h. einer Funktion der Form \(f(x) = x^T \cdot w + b\). Dabei ist \(w \in \mathbb{R}^n, b \in \mathbb{R}\). Um das Problem auf ein lineares zu reduzieren kann man den Feature-Vektor \(x\) durch ein konstantes Feature \(x_0 = 1\) erweitern. </dd> <dt><dfn>Korrelationskoeffizient</dfn></dt> <dd>Der Korrelationskoeffizient \(\kappa(X, Y) \in [-1, 1]\) ist ein Maß für den linearen Zusammenhang zwischen zwei Zufallsvariablen \(X, Y\). Er ist definiert als \[\kappa(X, Y) := \frac{Cov(X, Y)}{\sigma(X) \cdot \sigma(Y)}\]</dd> <dt><a href="https://de.wikipedia.org/wiki/Gau%C3%9F-Prozess"><dfn>Gausscher Prozess</dfn></a> (<dfn>Kriging</dfn>, <a href="https://www.youtube.com/watch?v=4vGiHC35j9s">Machine learning - Introduction to Gaussian processes</a> by Nando De Freitas)</dt> <dd>Gaussche Prozesse approximieren eine Funktion dadurch, dass sie an jedem Punkt eine Normalverteilung (Gauss-Verteilung) annehmen.<br /> <br /> Siehe <a href="https://en.wikipedia.org/wiki/Kriging">Gaussian process regression</a>.</dd> </dl> <h3 id="deep-learning">Deep Learning</h3> <p>Slides: <code>08_DeepLearning.pdf</code></p> <p>Siehe auch:</p> <ul> <li><a href="//martin-thoma.com/neuronale-netze-vorlesung/">Neuronale Netze Vorlesung</a></li> <li>Udacity: <a href="https://class.coursera.org/neuralnets-2012-001/lecture">Neural Networks for Machine Learning</a> by Hinton.</li> </ul> <dl> <dt><dfn>Deep Belief Netz</dfn> (<dfn>DBN</dfn>)</dt> <dd>Ein Deep Belief Netz ist ein gerichtetes, azyklisches, probabilistisches graphisches Modell.</dd> <dt><dfn>Restricted Boltzmann Machine</dfn> (<dfn>RBM</dfn>)</dt> <dd>Eine <i>RBM</i> ist ein neuronales Netz mit nur einem Hidden Layer. Es ist gleichzeitig ein Spezialfall von <abbr title="Markov Random Fields">MRFs</abbr>. Es werden keine Verbindungen zwischen den Hidden Units erlaubt (daher das "restricted" - Quelle: <a href="https://youtu.be/IcOMKXAw5VA?t=5m42s">Hinton, 2015</a>).<br /> <br /> Siehe <a href="https://www.cs.toronto.edu/~hinton/absps/guideTR.pdf">A Practical Guide to Training Restricted Boltzmann Machines</a> von Hinton, 2010.</dd> <dt><dfn>Contrastive Divergence</dfn> (<dfn>CD</dfn>, siehe <a href="https://www.youtube.com/watch?v=MD8qXWucJBY">YouTube Video</a> von Hugo Larochelle)</dt> <dd>Contrastive Divergence ist ein Trainingsalgorithmus für RBMs. Ein Hyperparameter ist \(k \in \mathbb{N}\). Er geht wie folgt vor: <ol> <li>Lege den Trainingsvektor \(x^{(t)}\) an die Eingabeknoten an.</li> <li>Berechne die Wahrscheinlichkeit für jede Hidden Unit, dass diese gleich 1 ist. Setze sie mit dieser Wahrscheinlichkeit gleich 1.</li> <li>Berechne die Wahrscheinlichkeit für jeden Eingabeknoten, dass dieser gleich 1 ist. Setze ihn mit dieser Wahrscheinlichkeit gleich 1.</li> <li>Gehe zu Schritt 2. Wiederhole dies für \(k\) Schritte (dies wird auch Gibbs-Sampling genannt). Das, was nach dem \(k\)-fachem Gibbs-Sampling in der Eingabeschicht steht wird auch "negative sample \(\tilde x\)" genannt.</li> <li>Update der Parameter: \[\begin{align} W &amp;\leftarrow W + \alpha (h(x^{(t)}) {x^{(t)}}^T - h(\tilde x) {\tilde x}^T)\\ b &amp;\leftarrow b + \alpha (h(x^{(t)}) - h(\tilde x))\\ c &amp;\leftarrow c + \alpha (x^{(t)} - \tilde x) \end{align} \] wobei \(\alpha \in (0, 1) \) die Lernrate ist, \(b \in \mathbb{R}^n_h\) der Bias-Vektor der Hidden Units und \(c \in \mathbb{R}^{n_v}\) der Bias-Vektor der Eingabeknoten ist. \(h\) ist eine Zufallsvariable, welche der Hidden Layer ist. Diese sind abhängig von der Eingabeschicht. </li> </ol> In der Praxis funktioniert es schon mit \(k=1\) für Pre-Training. Wenn \(k\) groß ist konvergiert \(\tilde x\) gegen den wahren Modellwert. Das wäre dann eine Monte-Carlo Estimation. </dd> <dt><dfn>Contrastive Wake-Sleep Algorithm</dfn> (siehe <a href="https://www.youtube.com/watch?v=znQfKBOGnJ8">The wake-sleep algorithm</a> von Hinton - Lecture 13d aus "<a href="https://www.coursera.org/course/neuralnets">Neural Networks for Machine Learning</a>")</dt> <dd>Der Wake-Sleep Algorithmus ist ein Trainingsalgorithmus für gerichtete graphische Modelle wie Sigmoid Belief Networks. Er ist nicht für RBMs. Man hat im Grunde zwei Netzwerke mit der gleichen Topologie, jedoch ist die Richtung vertauscht: Das eine Netz stellt die Hypothese aus den Daten auf, das andere Netz geniert neue Daten aus einer gegebenen Hypothese. In der <b>wake phase</b> wird die Eingabe genutzt um die Hypothese zu erzeugen. In dieser Phase werden die Gewichte für das Generative Modell trainiert. Dieses soll die Aktivierung der vorhergehenden Schicht rekonstruieren. In der <b>sleep phase</b> wird das generative Modell genutzt um aus dem Modell samples zu erzeugen. Dann trainiert man die Gewichte des erkennenden Netzes (also vergleichbar mit der wake phase, nur anders rum). <br /> Siehe <a href="http://www.cs.toronto.edu/~fritz/absps/ncfast.pdf">A Fast Learning Algorithm for Deep Belief Nets</a></dd> </dl> <h4 id="probleme-von-tiefen-netzen-und-wie-man-sie-lsen-kann">Probleme von Tiefen Netzen und wie man sie lösen kann:</h4> <ul> <li><strong>Lange Trainingsdauer</strong>: GPUs / mehr Rechenpower / weniger Parameter durch Parameter sharing, z.B. in <abbr title="Convolutional Neural Networks">CNNs</abbr> / <abbr title="Time Delay Neural Networks">TDNNs</abbr></li> <li><strong>Extrem viele gelabelte Trainingsdaten werden benötigt</strong>: Internet (z.B. Wikipedia, Soziale Netzwerke, Amazon Mechanical Turk) reduziert dieses Problem; Nutzen ungelabelter Daten durch <abbr title="Semi-Supervised Learning">SSL</abbr> in Auto-Encodern</li> <li><strong>Lokale Minima</strong></li> <li><strong>Overfitting</strong>: Regularis</li> </ul> <h4 id="siehe-auch">Siehe auch</h4> <ul> <li><a href="http://www.cs.toronto.edu/~hinton/adi/index.htm">MNIST Demo</a> (Flash): Neuronales Netz welches Ziffern generiert</li> <li>Geoffry Hinton: <a href="https://www.youtube.com/watch?v=IcOMKXAw5VA">Deep Learning</a> on YouTube, 2015. 43 minutes. (Topics: RBMs)</li> </ul> <h3 id="convolutional-neural-networks">Convolutional Neural Networks</h3> <p>Slides: <code>09_ConvolutionalNeuralNetworks.pdf</code></p> <p>Siehe auch: <a href="//martin-thoma.com/neuronale-netze-vorlesung/">Neuronale Netze Vorlesung</a></p> <dl> <dt><a href="https://de.wikipedia.org/wiki/Convolutional_Neural_Network"><dfn>Convolutional Neural Networks</dfn></a> (<dfn>CNNs</dfn>)</dt> <dd><abbr title="Convolutional Neural Networks">CNNs</abbr> sind neuronale Netze welche weight sharing einsetzen. Sie setzen eine diskrete Faltung um. Ein CNN muss mindestens einen <i>Convolutional Layer</i> haben. Dieser hat folgende Parameter: <ul> <li>Padding: None, Zero, Copy</li> <li>Stride: \(s \in \mathbb{N}_{&gt; 0}\)</li> <li>Filter Size: \((x,y) \in \mathbb{N}^2\)</li> <li>Number of filters: How many filters should get learned?</li> </ul></dd> <dt><dfn>Feature Map</dfn></dt> <dd>Nach einem Convolutional Layer hat man die Ausgabe der Filter, welche auf die Eingabe angewandt wurden. Diese nennt man <i>Feature Map</i>. Für jeden Filter bekommt man eine Feature Map. Die Feature Maps sind wiederum Eingaben für die nächsten Schichten.</dd> <dt><dfn>Pooling Layer</dfn></dt> <dd>Ein <i>pooling layer</i> ist eine Schicht in einem CNN, welche Features zusammenfasst. Pooling Schichten haben folgende Parameter: <ul> <li>Größe: Typischerweise \(3 \times 3\)</li> <li>Stride \(s \in \mathbb{N}\): Typischerweise gleich der Größe des Pooling-Bereichs (also 3).</li> <li>Art: max, mean</li> </ul> Typischerweise reduziert sie die Anzahl der Features, da typischerweise ein \(s &gt; 1\) gewählt wird.</dd> </dl> <h3 id="spiking-neural-nets">Spiking Neural Nets</h3> <p>Slides: <code>10_SpikingNeuralNets.pdf</code></p> <dl> <dt><a href="https://de.wikipedia.org/wiki/Gepulste_neuronale_Netze"><dfn>Spiking Neural Networks</dfn></a></dt> <dd>Gepulste neuronale Netze versuchen natürliche neuronen realistisch abzubilden. Das Hodgkin-Huxley Neuronenmodell wurde bereits 1952 vorgestellt.</dd> <dt><dfn>Hodgkin-Huxley Neuronenmodell</dfn></dt> <dd>Das <i>Hodgkin-Huxley Neuronenmodell</i> modelliert die elektrochemischen Vorgänge innerhalb eines Neurons mit elektrischen Baugliedern. Dies resultiert in Differenzialgleichungen mit 4&nbsp;Variablen (Kapazität der Membran, Widerstände der Ionenkanäle, Gleichgewichtspotentiale, Öffnung der Ionenkanäle). Das Modell ist realistisch, aber sehr komplex. </dd> <dt><dfn>LIF Neuronenmodell</dfn> (Leaky integrate and Fire)</dt> <dd>Das <i>LIF Neuronenmodell</i> modelliert ein Neuron durch eine gewöhnliche Differentialgleichung erster Ordnung.</dd> <dt><dfn>SRM Neuronenmodell</dfn> (Spike Response Model)</dt> <dd>Das <i>SRM Neuronenmodell</i> modelliert die Refraktionszeit. Das ist die Zeit, in der kein neues Aktionspotential aufgebaut werden kann. Das SRM ist ein rein phänomenologisches Modell, welches trotz der Einfachheit allgemeiner ist als das LIF-Modell.</dd> </dl> <h3 id="evaluation">Evaluation</h3> <p>Slides: <code>11_Evaluation.pdf</code></p> <h4 id="fr-klassifikation">Für Klassifikation:</h4> <dl> <dt><a href="https://de.wikipedia.org/wiki/Konfusionsmatrix"><dfn>Konfusionsmatrix</dfn></a></dt> <dd>Eine Konfusionsmatrix ist eine Tabelle, in welcher die Spalten angeben, welche Hypothese gemacht wurde (Testentscheid) und die Zeilen den wahren Wert angeben. So kann für beliebig viele Klassen gezeigt werden, wie gut der Klassifikator ist und welche Art der Verwechslung er macht.</dd> <dt><dfn>Klassifikationsfehler</dfn></dt> <dd>\(\text{Klassifikationsfehler} = \frac{\text{Fehlerhafte Hypothesen}}{\text{Anzahl aller Beispiele}} \in [0, 1]\)</dd> <dt><dfn>Klassifikationsgüte</dfn></dt> <dd>Klassifikationsgüte = 1 - Klassifikationsfehler</dd> <dt><dfn>False Alarm Rate</dfn> (<dfn>FA</dfn>, <dfn>Falsch Positiv Rate</dfn>, <dfn>FPR</dfn>)</dt> <dd>Es sei FP die Anzahl der False Positive Testdaten, also der Testdaten für welche <i>Positive</i> vorhergesagt wurde, die aber negative sind. Weiter sei TN die Anzahl der True Negatives, also der Testdaten, für welche korrekterweise negative vorhergesagt wurde. Dann ist die <i>FPR</i> definiert als \[\text{FPR} := \frac{FP}{FP + TN} \in [0, 1]\] Die FPR gibt also den Anteil an, wie viele der tatsächlich negativen fälschlicherweise als positiv erkannt wurden.</dd> <dt><dfn>Miss-Rate</dfn> (<dfn>MR</dfn>, <dfn>Falsch Negativ Rate</dfn>, <dfn>FNR</dfn>)</dt> <dd>\[FNR := \frac{FN}{TP + FN} \in [0, 1]\]</dd> <dt><dfn>Recall</dfn> (<dfn>True Positive Rate</dfn>, <dfn>TPR</dfn>, <dfn>Sensitivität</dfn>)</dt> <dd>\[TPR = \frac{TP}{TP + FN} = 1 - FNR \in [0, 1]\] Der Recall gibt den Anteil der erkannten positiven aus allen positiven an. <i>Sensitivität</i> ist ein in der Medizin üblicher Begriff.</dd> <dt><dfn>Precision</dfn> (<dfn>Genauigkeit</dfn>)</dt> <dd>\[Precision = \frac{TP}{TP + FP} \in [0, 1]\] Die Precision gibt den Anteil der real positiven aus den als positiv erkannten an.</dd> <dt><dfn>ROC-Graph</dfn> (<dfn>Receiver-Operator Curve</dfn>)</dt> <dd>Der ROC-Graph gibt für einen Klassifikator, bei dem man einen Parameter einstellen kann, den Fehler an. Die \(x\)-Achse ist dabei die FPR, die \(y\)-Achse die TPR.</dd> <dt><dfn>Spezifität</dfn></dt> <dd>Der Begriff der <i>Spezifität</i> ist in der Medizin üblich und ist definiert durch \[Spezifität = \frac{TN}{TN + FP} = 1 - FPR\] Es ist eine Art recall für die negative Klasse. Im Beispiel eines medizinischen Tests wäre das der Anteil der Gesunden, bei denen tatsächlich auch die Diagnose "Gesund" gestellt wurde.</dd> <dt><dfn>PRC-Graph</dfn> (<dfn>Precision-Recall-Graph</dfn>)</dt> <dd>Die \(x\)-Achse ist Recall, die \(y\)-Achse ist Precision.</dd> <dt><dfn>F-Maß</dfn></dt> <dd>\[F_\alpha = \frac{precision \cdot recall}{\alpha^2 \cdot precision + recall}\]</dd> </dl> <p>Alternative:</p> <ul> <li>Aufstellen einer Kostenfunktion und optimieren nach Kosten.</li> <li>Plotten der Anzahl der Trainingsdaten (<span>\(x\)</span>-Achse) und des Fehlers (<span>\(y\)</span>-Achse). Die Kurven sollten der Test-Fehler sowie der Trainingsfehler sein. Damit lässt sich abschätzen, ob mehr Trainingsdaten ohne eine Veränderung des Modells hilfreich sind.</li> </ul> <h4 id="fr-regression">Für Regression</h4> <dl> <dt><dfn>Mittlerer Quadratischer Fehler</dfn> (<dfn>MSE</dfn>, <dfn>Mean Squared Error</dfn>)</dt> <dd>\[E(f, data) = \frac{1}{|data|} \sum_{(x, y) \in data} (f(x) - y)^2\]</dd> <dt><dfn>Relativer Quadratischer Fehler</dfn></dt> <dd>\[E(f, data) = \frac{\sum_{(x, y) \in data} (f(x) - y)^2}{\sum_{(x,y) \in data} (y - \mu)^2}\]</dd> <dt><dfn>Mittlerer Absoluter Fehler</dfn></dt> <dd>\[E(f, data) = \frac{1}{|data|} \sum_{(x, y) \in data} |f(x) - y|\]</dd> </dl> <h4 id="siehe-auch-1">Siehe auch</h4> <ul> <li><a href="https://de.wikipedia.org/wiki/Beurteilung_eines_binären_Klassifikators">Beurteilung eines binären Klassifikators</a></li> <li><a href="https://en.wikipedia.org/wiki/False_positives_and_false_negatives">False positives and false negatives</a></li> <li>Matt Zeiler: <a href="https://www.youtube.com/watch?v=ghEmQSxT6tw">Visualizing and Understanding Deep Neural Networks</a> on YouTube, 2015. 48 minutes.</li> </ul> <h2 id="prfungsfragen">Prüfungsfragen</h2> <ul> <li>Was versteht man unter einer "Transductive SVM"?<br /> → Eine Transductive SVM ist eine <abbr title="Support Vector Machine">SVM</abbr> welche neben gelabelten Daten auch noch ungelabelte benutzt. Sie versucht die Trennebene durch eine Region geringer Dichte zu legen.</li> <li>Wie lautet die Optimierungsformel der transductive SVM?<br /> → \[\text{minimize}_{w, b, y^*} \frac{1}{2} \|w\|^2\] unter den Nebenbedingungen \[\forall i \in 1, \dots, n: y_i (w \cdot x_i - b) \geq 1\] und \[\forall j \in 1, \dots, k: y_j^* (w \cdot x_j^* -b) \geq 1\text{ with }y_j^* \in \{-1, 1\}\] Dabei sind \(D^* = \{x_i^* | i = 1, \dots, k\}\) ungelabelte Daten. </li> <li>Was macht man im Reinforcement Learning, wenn Aktionen länger dauern?<br /> → Options verwenden (TODO: Wie ändert sich die Value Iteration Formel nun bzgl. der Zeit?)</li> <li>Warum heißen POMDPs "Partially Observable"?<br /> → Weil der Agent zwar Feedback über die Umgebung bekommt, aber nicht direkt erfährt in welchem Zustand er ist. Siehe <a href="#pomdp-definition">Definition</a>.</li> <li>Welche Active Learning Techniken gibt es?<br /> → Query / Selective / Pool-based (vgl. <a href="#tocAnchor-1-1-4">Query-by-Committee</a>)</li> <li>Wie nennt man ein instanziiertes OPRM?<br /> → TODO (Skelett?)</li> <li>Wie funktioniert aktives Lernen bei SVMs?<br /> → Bei SVMs gibt es die Dualität zwischen dem Feature-Space und dem Hypothesenraum. In dem Feature-Space stellen die Achsen <span>\(x_i\)</span> die Features dar, Trainingsdaten Punkte sind und die SVM durch die Trennebene visualisiert wird. Im Hypothesenraum sind die Achsen <span>\(w_i\)</span> zusammen der Normalenvektor der SVM, die verschiedenen Trennebenen der SVMs sind hier Punkte. Die Daten geben Bedingungen an die SVM vor, welche in diesem Raum als Hyperebenen dargestellt werden können. Der Margin ist in diesem Raum ein Kreis, der die Bedingungs-Hyperebenen berührt. Beim aktiven lernen versucht man den Version-Space im Inneren der Bedungungs-Hyperebenen so schnell zu verkleinern wie möglich.</li> <li>Was versteht man unter Transduktivem Lernen?<br /> → Unter Transduktiver Inferenz versteht man das Schließen von Trainingsbeispielen direkt auf auf spezifische Testfälle.</li> <li>Wie nennt man die Wahrscheinlichkeit des aktiellen Zustands in POMDPs?<br /> → Belief.</li> </ul> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://tks.anthropomatik.kit.edu/28_176.php">Vorlesungswebsite</a></li> <li><a href="https://ilias.studium.kit.edu/goto_produktiv_crs_429082.html">Ilias</a>: Ist passwortgeschützt</li> <li><a href="//martin-thoma.com/machine-learning-1-course/">Zusammenfassung der Vorlesung ML 1</a></li> </ul> <h2 id="literatur">Literatur</h2> <ul> <li>[<a href="#ref-schu15-anchor" name="ref-schu15">Schu15</a>] J. Schulz. Erkennung von Interaktionen zwischen Verkehrsteilnehmern zur Verhaltensprädiktion. Masterarbeit am FZI. Karlsruhe, 2015. Man kann <a href="https://www.fzi.de/wir-ueber-uns/organisation/mitarbeiter/address/kuhnt/">Florian Kuhnt</a> um Zugang dazu fragen.</li> <li>[<a href="#ref-die00-anchor" name="ref-die00">Die00</a>] T. Dietterich. <a href="https://www.jair.org/media/639/live-639-1834-jair.pdf">Hierarchical Reinforcement Learning with the MAXQ Value Function Decomposition</a>. Journal of Artificial Intelligence Research, 2000.</li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <p>Es gibt keine Übungsblätter, keine Übungen, keine Tutorien und keine Bonuspunkte.</p> <h2 id="kontakt">Kontakt</h2> <ul> <li>goettl@fzi.de: Sonja Göttl (Sekretariat, zum Anmelden zur mündlichen Prüfung)</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Mündliche Prüfung (in Zukunft schriftlich)<br /> <strong>Ort</strong>: nach Absprache<br /> <strong>Zeit</strong>: 15 min<br /> <strong>Übungsschein</strong>: gibt es nicht<br /> <strong>Bonuspunkte</strong>: gibt es nicht<br /> <strong>Ergebnisse</strong>: werden ca. 5 - 10 min. nach der mündlichen Prüfung gesagt<br /> <strong>Erlaubte Hilfsmittel</strong>: keine</p> Neuronale Netze - Klausur //martin-thoma.com/neuronale-netze-vorlesung/ Mon, 27 Apr 2015 21:15:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/neuronale-netze-vorlesung <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Neuronale Netze&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://isl.anthropomatik.kit.edu/english/21_74.php">Herrn Prof. Dr. Alexander Waibel</a> im Sommersemester 2015 gehört. Der Artikel wird bis zur mündlichen Prüfung laufend erweitert.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="vorlesung">Vorlesung</h3> <table> <tr> <th>Datum</th> <th>Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>15.04.2015</td> <td><a href="https://ies.anthropomatik.kit.edu/ies/download/lehre/me/ME-Kap1_V33.pdf">Einleitung</a></td> <td>-</td> </tr> <tr> <td>21.04.2015</td> <td>LVQ and related Techiques</td> <td>k-Means, OLVQ1, kompetitives Lernen, Mode Seeker, PCA</td> </tr> <tr> <td>22.04.2015</td> <td>-</td> <td>Übung</td> </tr> <tr> <td>28.04.2015</td> <td>Perceptron</td> <td>-</td> </tr> <tr> <td>12.05.2015</td> <td>Auto-Encoder</td> <td>Denoising- und Sparse Autoencoder, Bottleneck-Features<a href="https://de.wikipedia.org/wiki/Kullback-Leibler-Divergenz">Kullback-Leibler-Divergenz</a>; <a href="https://de.wikipedia.org/wiki/Kettenregel#Mathematische_Formulierung">Kettenregel</a></td> </tr> <tr> <td>13.05.2015</td> <td>Deep Learning</td> <td>Momentum, Rprop, Newbob, L1/L2-Regularisierung (\(|w|\), \(w^2\)), weight decay</td> </tr> <tr> <td>19.05.2015</td> <td>Übung</td> <td>-</td> </tr> <tr> <td>20.05.2015</td> <td>Übung</td> <td>-</td> </tr> <tr> <td>26.05.2015</td> <td><abbr title="Self Organizing Map">SOM</abbr></td> <td>Hebbian Learning, "<abbr title="Vector Quantization">VQ</abbr>" mit SOM</td> </tr> <tr> <td>09.06.2015</td> <td>Effizientes Lernen</td> <td>Paralleles Lernen; Quickprop; Alternative Fehlerfunktion (cross entropy, <abbr title="Classification Figure of Merit">CFM</abbr>); weight elimination / regularization</td> </tr> <tr> <td>15.07.2015</td> <td>Summary</td> <td>When to use which objective function (cross entropy, MSE); Backpropagation; Weight initialization; Regularization (L2 weight decay, dropout); Time Delay NN; Recurrent Networks; Applications (Speech Recognition, Computer Vision)</td> </tr> </table> <h3 id="nn01-intropdf">NN01-Intro.pdf</h3> <ul> <li>Human Brain vs. Computer (Processing/Processors, Accuracy, Speed, Hardware, Design)</li> <li>Aufbau eines biologischen Neurons (vgl. <a href="https://de.wikipedia.org/wiki/Nervenzelle#.C3.9Cberblick_.C3.BCber_den_Aufbau_einer_Nervenzelle">Wikipedia</a>)</li> </ul> <h3 id="nn02-classificationpdf">NN02-Classification.pdf</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/12/perceptron-or.png"><img src="../images/2015/12/perceptron-or.png" alt="Rosenblatt-Perceptron which realizes logical or" width="" height="" class="" /></a><p class="wp-caption-text">Rosenblatt-Perceptron which realizes logical or</p></div> <ul> <li>McCullch-Pitts Neuron (weights, bias, activation function is step function)</li> <li>Rosenblatt Perceptron Algorithmus</li> <li>Backpropagation</li> <li>Curse of Dimensionality</li> <li><a href="https://de.wikipedia.org/wiki/Kerndichtesch%C3%A4tzer">Parzen Window</a></li> <li>Features: Nominal, Ordinal, Intervallskaliert, Verhältnisskaliert</li> </ul> <dl> <dt><dfn>Bayes-Rule</dfn> (Source: <a href="https://en.wikipedia.org/wiki/Bayes%27_rule">wikipedia</a>)</dt> <dd>Given events \(A_1\), \(A_2\) and \(B\), Bayes' rule states that the conditional odds of \(A_1:A_2\) given \(B\) are equal to the marginal odds of \(A_1:A_2\) multiplied by the Bayes factor or likelihood ratio \(\Lambda\): \[O(A_1:A_2|B) = \Lambda(A_1:A_2|B) \cdot O(A_1:A_2) ,\] where \[\Lambda(A_1:A_2|B) = \frac{P(B|A_1)}{P(B|A_2)}.\]</dd> <dt><dfn>Parametrischer Klassifizierer</dfn></dt> <dd>Ein Klassifizierer heißt <i>parametrisch</i>, wenn er eine Wahrscheinlichkeitsverteilungsannahme macht.</dd> <dt><dfn>Naiver Bayes-Klassifikator</dfn></dt> <dd>Ein Klassifizierer heißt naiver Bayes-Klassifikator, wenn er den Satz von Bayes unter der naiven Annahme der Unabhängigkeit der Features benutzt.</dd> <dt><dfn>Normalverteilung</dfn></dt> <dd>Eine stetige Zufallsvariable \(X\) mit der Wahrscheinlichkeitsdichte \(f\colon\mathbb{R}\to\mathbb{R}\), gegeben durch<br /> \(f(x) = \frac {1}{\sigma\sqrt{2\pi}} e^{-\frac {1}{2} \left(\frac{x-\mu}{\sigma}\right)^2}\)<br /> heißt \(\mathcal N\left(\mu, \sigma^2\right)\)-verteilt, normalverteilt mit den Erwartungswert \(\mu\) und Varianz \(\sigma^2\).</dd> <dt><dfn>Multivariate Normalverteilung</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Mehrdimensionale_Normalverteilung">Wikipedia</a>)</dt> <dd>Eine \(p\)-dimensionale reelle Zufallsvariable \(X\) ist normalverteilt mit Erwartungswertvektor \(\mu\) und (positiv definiter) Kovarianzmatrix \(\Sigma\), wenn sie eine Dichtefunktion der Form \[f_X(x)=\frac{1}{ \sqrt{(2\pi)^p \det(\Sigma)} } \exp \left( -\frac{1}{2}(x-\mu)^{T}\Sigma^{-1}(x-\mu) \right)\] besitzt. Man schreibt \[X\sim \mathcal N_p(\mu, \Sigma).\]</dd> <dt><dfn>Gauß'scher Klassifizierer</dfn></dt> <dd>Ein (naiver) Bayes-Klassifikator, welcher von normalverteilten Daten ausgeht heißt <i>Gauß'scher Klassifizierer</i>.</dd> <dt><dfn>Principal Component Analysis</dfn> (<dfn>PCA</dfn>, <dfn>Hauptkomponentenanalyse</dfn> - vgl. <a href="https://en.wikipedia.org/wiki/Principal_component_analysis">Wikipedia</a>)</dt> <dd>Die Hauptkomponentenanalyse ist ein Verfahren zur Dimensionalitätsreduktion von ungelabelten Daten im \(\mathbb{R}^n\). Sie projeziert die Daten auf diejenige Hyperebene im \(\mathbb{R}^d\), die den durch die Projektion stattfindenden Datenverlust minimal hält. Dabei ist \(d \in 1, \dots, n\) beliebig wählbar. Die Transformation der Daten \(X\) findet durch eine Matrixmultiplikation \(Y = P \cdot X\) statt. Die Matrix \(P\) besteht aus den ersten \(d\) Eigenvektoren der Kovarianzmatrix der Features \(X\): \(P = (v_1, \dots, v_d)\) mit \(\lambda_j v_j = C_X v_j\) für \(j=1,\dots,d\) Außerdem gilt: \(C_X = \frac{1}{n-1} X X^T\) </dd> </dl> <h3 id="v04-perceptron">V04: Perceptron</h3> <p>Slide name: <code>V04_2015-04-28_Perceptron.pdf</code></p> <dl> <dt><dfn>McCulloch–Pitts (MCP) Neuron</dfn></dt> <dd>Ein MLP-Neuron is ein Algorithmus zur binären Klassifizierung. Er hat \(m+1\), mit \(m \in \mathbb{N}_{&gt; 0}\) inputs \(x_i \in \{0, 1\}\). Davon ist der erste (nullte) Konstant gleich Eins und wird <i>Bias</i> genannt. Jeder Input wird mit eingem Gewicht \(w_i \in \mathbb{R}\) multipliziert, alle gewichteten Inputs werden addiert und schließlich wird die Stufenfunktion \(\varphi(x) = \begin{cases}1 &amp;\text{falls } x &gt; 0\\0 &amp;\text{sonst} \end{cases}\) angewendet. </dd> <dt><dfn>Rosenblatt-Perzeptron</dfn></dt> <dd>Wie das McCulloch–Pitts (MCP) Neuron, nur ist \(x_i \in \mathbb{R}\) und ein Lernalgorithmus ist gegeben. Dieser addiert den \(\lambda \in (0, 1)\) gewichteten, fehlklassifizierten Vektor auf die Gewichte \(w_i\). \(\lambda\) heißt die <i>Lernrate</i>. </dd> <dt><dfn>Pocket Perceptron Algorithm</dfn></dt> <dd>Ein Lernalgorithmus für ein Rosenblatt-Perzeptron. Dieser konvergiert zu Gewichten, welche die wenigsten Beispiele falsch klassifiziert. </dd> <dt><dfn>Sigmoid-Funktion</dfn></dt> <dd>\(\varphi(x) = \frac{1}{1+e^{-x}}\)</dd> <dt><dfn>Softmax-Funktion</dfn></dt> <dd>\(\varphi(a_i) = \frac{e^{a_i}}{\sum_{k} e^{a_k}}\) wobei \(a_i\) die Aktivierung des \(i\)-ten Neurons der selben Schicht ist.</dd> <dt><dfn>Perzeptron</dfn> / <dfn>Logistic Neuron</dfn></dt> <dd><abbr title="Mean Squared Error">MSE</abbr> + Sigmoid activation function</dd> </dl> <p>Fakten:</p> <ul> <li>Das Rosenblatt-Perzeptron findet eine lineare Trenngrenze, wenn sie existiert.</li> <li>Probleme vom Rosenblatt-Perzeptron: <ul> <li>XOR</li> <li>Nicht-linear trennbare Daten</li> <li>Nicht-trennbare Daten</li> <li>Wahl der Lernrate und der Startgewichte</li> </ul> </li> <li>Aufbau eines biologischen Neurons (Axon, Dendriten, Zellkörper, Ranviersche Schnürringe, Synapsen)</li> <li>Glia-Zellen</li> </ul> <p>Fragen:</p> <ul> <li>Folie 6: Ist der Input nicht in [0, 1]?</li> </ul> <h3 id="v05-features">V05: Features</h3> <p>Slide name: <code>V05_2015-04-29_Features.pdf</code></p> <dl> <dt><dfn>Rectified Linear Unit</dfn> (<dfn>ReLU</dfn>)</dt> <dd>\(\varphi(x) = \max(0, x)\)</dd> <dt><dfn>Softplus</dfn></dt> <dd>\(\varphi(x) = \log(1 + e^x)\)</dd> <dt><dfn>Feed Forward Neural Network</dfn></dt> <dd>A Feed Forward Neural Network is a learning algorithm which takes a fixed-size input feature vector, applies varous matrix multiplications and point-wise non-linear functions to obtain a fixed-size output vector.</dd> <dt><dfn>Multilayer Perceptron</dfn></dt> <dd>A Multilayer Perceptron is a special type of Feed Forward Neural Network. It consists of fully connected layers only.</dd> <dt><dfn>Metrik</dfn> (siehe <a href="https://de.wikipedia.org/wiki/Metrischer_Raum#Formale_Definition">Wikipedia</a>)</dt> <dd>Sei \(X\) eine Menge und \(d:X \times X \rightarrow \mathbb{R}\) eine Abbildung. \(d\) heißt Metrik auf \(X\), wenn gilt: <ul> <li>\(d(x, y) = 0 \geq x=y \;\;\; \forall x, y \in X\)</li> <li>\(d(x,y)=d(y,x=\)</li> <li>\(d(x,y) \leq d(x,z) + d(z,y)\)</li> </ul> </dd> <dt><dfn>Jaccard-Metrik</dfn> (siehe <a href="https://de.wikipedia.org/wiki/Jaccard-Koeffizient#Jaccard-Metrik">Wikipedia</a>)</dt> <dd>Es seien \(A, B\) Mengen und \(J(A, B) := \frac{|A \cup B| - |A \cap B|}{|A \cup B|}\). Dann heißt \(J\) die Jaccard-Metrik. </dd> <dt><dfn>Levenshtein-Distanz</dfn> (siehe <a href="https://de.wikipedia.org/wiki/Levenshtein-Distanz">Wikipedia</a>)</dt> <dd>Es seien \(a, b\) Zeichenketten, \(|a|\) die Länge der Zeichenkette \(a\) und \(\delta_{a_i \neq b_j}\) genau dann 1, wenn das \(i\)-te Zeichen von \(a\) und das \(j\)-te Zeichen von \(b\) sich unterscheiden. Dann heißt \(d_L(a, b)\) die Levenshtein-Distanz: \[d_L(a,b) := lev_{a,b}(|a|, |b|)\] \[\text{lev}_{a,b}(i, j) = \begin{cases}\max(i,j) &amp;\text{falls} \min(i,j) = 0,\\ \min \begin{cases}\text{lev}_{a,b}(i-1,j)+1\\ \text{lev}_{a,b}(i,j-1)+1\\ \text{lev}_{a,b}(i-1,j-1)+\delta_{(a_i \neq b_j)}\\\end{cases} &amp;\text{sonst}\end{cases}\] </dd> </dl> <p>Fragen:</p> <ul> <li>Welche Feed Forward Neuronalen Netze existieren, die keine Multilayer Perceptronen sind?</li> <li>Welche Skalentypen gibt es für Merkmale (Features)? <ul> <li>Nominale Merkmale: Nur Gleichheit kann überprüft werden</li> <li>Ordinale Merkmale: Es existiert eine “kleiner gleich”-Relation</li> <li>Intervallskalierte Merkmale: <ul> <li>Die Differenz der Merkmale hat eine Semantik</li> <li>Es existiert jedoch kein “wirklicher” Nullpunkt</li> </ul> </li> <li>Verhältnisskalierte Merkmale: Wie Intervallskaliert, aber mit absolutem Nullpunkt.</li> </ul> </li> </ul> <h3 id="v06-backpropagation">V06: Backpropagation</h3> <p>Slide name: <code>V06_2015-05-05_Backpropagation.pdf</code></p> <dl> <dt><dfn>Kreuzentropie Fehlerfunktion</dfn> (<dfn>Cross-Entropy</dfn>, vgl. <a href="https://de.wikipedia.org/wiki/Kreuzentropie">Wikipedia</a>)</dt> <dd>\[E_{-x} = - \sum_{k}[t_k^x \log(o_k^x) + (1-t_k^x) \log (1- o_k^x)]\] wobei \(x\) der Feature-Vektor ist, \(k\) ein Neuron des letzen Layers, \(t\) der wahre Wert (d.h. der gewünschte Output), \(o\) der tatsächliche Output ist.</dd> </dl> <ul> <li>Stochastic Gradient Descent</li> <li>Batch Gradient Descent</li> </ul> <h3 id="v07-feature-learning">V07: Feature Learning</h3> <p>Slide name: <code>V07_12-05-2015_Feature_Learning.pdf</code></p> <dl> <dt><dfn>Autoencoder</dfn> (vgl. <a href="https://en.wikipedia.org/wiki/Autoencoder">Wikipedia</a>)</dt> <dd>Ein Autoencoder ist ein neuronales Netz, welches darauf trainiert wird die Input-Daten am Output wieder zu replizieren.</dd> <dt><dfn>Bottleneck Features</dfn></dt> <dd>Unter Bottleneck-Features versteht man eine Schicht in einem neuronalem Netz, welche wesentlich kleiner ist als die vorhergehende und nachfolgende Schicht.</dd> <dt><dfn>Kullback-Leibler-Divergenz</dfn> (vgl. <a href="https://en.wikipedia.org/wiki/Kullback%E2%80%93Leibler_divergence">Wikipedia</a>)</dt> <dd>Die Kullback-Leibler-Divergenz ist ein Maß für die Unterschiedlichkeit zweier Wahrscheinlichkeitsverteilungen \(P, Q\). Für diskrete Verteilungen ist sie definiert als: \[KL(P||Q) := \sum_{x \in X} P(x) \cdot \log \frac{P(x)}{Q(x)}\]</dd> <dt><dfn>Denoising Autoencoder</dfn></dt> <dd>Ein Autoencoder, welcher trainiert wird rauschen zu entfernen.</dd> </dl> <p>Fakten:</p> <ul> <li>Eine lineare Aktivierungsfunktion wird in einer Repräsentation im Bottleneck-Feature resultieren, die PCA ähnelt.</li> <li>Fehlerfunktion: <ul> <li><abbr title="Cross Entropy">CE</abbr> bei binären Ausgaben (d.h. Input-Features)</li> <li><abbr title="Mean squared error">MSE</abbr> bei reelen Ausgaben (d.h. Input-Features)</li> </ul> </li> </ul> <p>Fragen:</p> <ul> <li>Wie muss man die Grafik zu Stacked Denoising Autoencodern verstehen?</li> </ul> <h3 id="v08-deep-learning">V08: Deep Learning</h3> <p>Slide name: <code>V08_2015-05-13_Deep_Learning.pdf</code></p> <dl> <dt><dfn>Deep Neural Networks</dfn></dt> <dd>Neural Networks with at least two hidden layers with nonlinear activation functions.</dd> <dt><dfn>Hyperparameter</dfn></dt> <dd>Hyperparameter \(\theta\) eines neuronalen Netzes sind Parameter, welche nicht gelernt werden.</dd> <dt><dfn>Learnin Rate Scheduling</dfn></dt> <dd>Start with a learning rate \(\eta\) and reduce it while training</dd> <dt><dfn>Exponential Decay Learning Rate</dfn></dt> <dd>\(\eta_t = \eta_{t-1} \cdot \alpha = \eta_0 \cdot \alpha^t\) mit \(\alpha \in (0, 1)\)</dd> <dt><dfn>Performance Scheduling</dfn></dt> <dd>Measure the error on the cross validation set and decrease the learning rate when the algorithm stops improving.</dd> <dt><dfn>RProp</dfn> (siehe <a href="https://en.wikipedia.org/wiki/Rprop">Wikipedia</a>)</dt> <dd>RProp is a learning rate scheduling method which is only based on the sign of the gradient. It increases the learning rate when the sign of the gradient doesn't change and increases it when the sign of the gradient changes.</dd> <dt><dfn><abbr title="adaptive gradient">AdaGrad</abbr></dfn> (siehe <a href="https://en.wikipedia.org/wiki/Stochastic_gradient_descent#AdaGrad">Wikipedia</a>)</dt> <dd>\[\eta_{tij} = \frac{\eta_0}{\sqrt{1 + \sum_k {(\frac{\partial E^{t-k}}{\partial w_{ij}})}^2}}\]</dd> <dt><dfn>Newbob Scheduling</dfn></dt> <dd>Newbob scheduling is a combination of Exponential decay learning rate scheduling and performance scheduling. It starts with a learning rate \(\eta_0\). When the validation error stops decreasing, switch to exponentially decaying learning rate. Terminate when the validation error stops decreasing again.</dd> <dt><dfn>Cross Entropy Error function</dfn> (CE)</dt> <dd>\[E_{CE}(w) = - \sum_{x \in X} \sum_{k} [t_k^x \log(o_k^x + (1-t_k^x) \log(1-o_k^x))]\] where \(w\) is the weight vector, \(X\) is the set of training examples (feature vectors), \(t_k^x = \begin{cases}1 &amp;\text{if } x \text{ is of class }k\\0&amp;\text{otherwise}\end{cases}\) and \(o_k^x\) is the output at neuron \(k\) of the network for the feature vector \(x\).</dd> <dt><dfn>Mean Squared Error function</dfn> (MSE)</dt> <dd>\[E_{MSE}(w) = \frac{1}{2}\sum_{x \in X} \sum_{k} (t_k^x - o_k^x)^2\] where \(w\) is the weight vector, \(X\) is the set of training examples (feature vectors), \(t_k^x = \begin{cases}1 &amp;\text{if } x \text{ is of class }k\\0&amp;\text{otherwise}\end{cases}\) and \(o_k^x\) is the output at neuron \(k\) of the network for the feature vector \(x\).</dd> </dl> <ul> <li>Pretraining</li> <li>TDNNs CNNs</li> <li>Design choices (hyperparameters): <ul> <li>Topology (Width of layers, number of layers)</li> <li>Activation functions</li> <li>Error function</li> <li>Mini-Batch size</li> <li>Training function</li> <li>Preprocessing</li> <li>Initial Weights</li> </ul> </li> <li>MSE vs CE: <ul> <li>MSE penetalizes large differences much more than small ones</li> <li>MSE works well for function approximation</li> <li>CE works well on classification tasks</li> </ul> </li> </ul> <p>Fragen:</p> <ul> <li>AdaGrad (Folie 34)</li> <li>Optimal drain damage (Folie 36)</li> </ul> <h3 id="v09-reinforcement-learning">V09: Reinforcement Learning</h3> <p>Slide name: <code>V09_2015-05-26-Reinforcement-Learning.pdf</code></p> <dl> <dt><dfn>Markov Decision Process</dfn> (<dfn>MDP</dfn>, vgl. <a href="https://de.wikipedia.org/wiki/Markow-Entscheidungsproblem">Wikipedia</a>)</dt> <dd>Ein Markovscher Entscheidungsprozess ist ein 5-Tupel \((S, A, T, r, p_0)\), wobei <ul> <li>\(S\) eine endliche Zustandsmenge,</li> <li>\(A\) eine endliche Menge von Aktionen,</li> <li>\(T_a(s, s') = T(s_{t+1}=s'|s_t = s, a_t = a)\) die Wahrscheinlichkeit zu einem beliebigen Zeitpunkt von Zustand \(s\) mit der Aktion \(a\) in den Zustand \(a'\) zu kommen (engl. Transition),</li> <li>\(r_a(s, s')\) ist die Belohnung (Reward), die man direkt erhält wenn man erhält wenn man von Zustand \(s\) mit Aktion \(a\) in Zustand \(s'\) kommt,</li> <li>\(p_0\) ist die Startverteilung auf die Zustände \(S\)</li> </ul> </dd> <dt><dfn>Diskontierungsfaktor</dfn></dt> <dd>Ein Diskontierungsfaktor \(\gamma \in [0, 1]\) encodiert den Bedeutungsverlust zwischen einer direkten Belohnung und einer späteren Belohnung. Es sollte \(\gamma &lt; 1\) gelten um unendliche Belohnungen zu vermeiden.</dd> <dt><dfn>Strategie</dfn> (engl. <dfn>Policy</dfn>)</dt> <dd>Eine Strategie \(\pi:S \rightarrow A\) sagt einem Agenten welche Aktion er in welchem Zustand ausführen soll.</dd> <dt><dfn>Q-Funktion</dfn> (Action-Value function)</dt> <dd>Die Q-Funktion \(Q^\pi: S \times A \rightarrow \mathbb{R}\) weißt jeder Aktion in jedem Zustand einen Wert zu unter der Annahme, dass die Strategie \(\pi\) genutzt wird.</dd> <dt><dfn>V-Funktion</dfn> (State-Value function)</dt> <dd>Die V-Funktion \(V^\pi: S \rightarrow \mathbb{R}\) weißt jeder jedem Zustand die Erwartete Belohnung zu unter der Annahme, dass die Strategie \(\pi\) genutzt wird.</dd> <dt><dfn>\(\varepsilon\)-Greedy Strategy</dfn></dt> <dd>Explore \(\varepsilon\)% of the time. Otherwise, follow what you currently believe is best.</dd> <dt><dfn>\(\varepsilon\)-decreasing Strategy</dfn></dt> <dd>Explore \(\varepsilon\)% of the time. Otherwise, follow what you currently believe is best. Reduce \(\varepsilon\) over time.</dd> <dt><dfn>\(\varepsilon\)-first Strategy</dfn></dt> <dd>Explore for \(\varepsilon\) steps and then do what you think is best.</dd> <dt><dfn>Adaptive \(\varepsilon\)-greedy Strategy</dfn></dt> <dd>Explore \(\varepsilon\)% of the time. Otherwise, follow what you currently believe is best. Reduce \(\varepsilon\) based on what you learn.</dd> <dt><dfn>Episode</dfn></dt> <dd>A run through an <abbr title="Markov Decision Process">MDP</abbr> from a start state to an end state.</dd> <dt><dfn>Monte Carlo Policy Evaluation</dfn></dt> <dd>Initialize state values \(V^\pi\) and iterate: <ol> <li>Generate an episode</li> <li>foreach state \(s\) in episode: <ol> <li>Get the reward \(\hat{R}\) from that state on</li> <li>\(\hat{R} = \sum_{j=0}^\infty \gamma^j r_j\)</li> <li>\(V_{k+1}^\pi (s) \leftarrow V_k^pi (s) (1-\alpha)+\alpha \hat{R}\)</li> </ol> </li> </ol> where \(\alpha\) is the learning rate. </dd> <dt><dfn>Temporal Difference Learning</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Temporal_Difference_Learning">Wikipedia</a>)</dt> <dd>TODO?</dd> </dl> <p>Konvention:</p> <ul> <li>Eine optimale Strategie wird mit <span>\(\pi^*\)</span> bezeichnet.</li> </ul> <p>Fragen:</p> <ul> <li>Was bedeutet es, wenn in einem MDP der Diskontierungsfaktor (\gamma = 0) ist? → Nur der aktuelle Reward ist wichtig. Effektiv nimmt der Agent immer das nächste Feld, welche den höchsten Reward bietet (bzw. die Aktion, die den größten 1-Aktion Erwartungswert liefert).</li> <li>Was bedeutet es, wenn in einem MDP der Diskontierungsfaktor (\gamma = 1) ist? → Der Agent versucht die Summe der Belohnungen insgesamt zu maximieren.</li> </ul> <p>TODOs:</p> <ul> <li>What is Policy Iteration?</li> <li>SARSA - State-Action-Reward-State-Action</li> <li>Q-Learning</li> </ul> <h3 id="v10-som">V10: SOM</h3> <p>Slide name: <code>V10_2015-05-26_SOM.pdf</code></p> <dl> <dt><dfn>Selbstorganisierende Karten</dfn> (<dfn>SOM</dfn>, <dfn>Kohonennetze</dfn>, vgl. <a href="https://de.wikipedia.org/wiki/Selbstorganisierende_Karte">Wikipedia</a>)</dt> <dd>SOMs sind eine Art von Neuronalen Netzen.</dd> </dl> <p>Siehe auch:</p> <ul> <li><a href="https://codesachin.wordpress.com/2015/11/28/self-organizing-maps-with-googles-tensorflow/">Self-Organizing Maps with Google’s TensorFlow</a></li> <li><a href="http://www.ai-junkie.com/ann/som/som1.html">Kohonen’s Self Organizing Feature Maps</a> by ai-junkie</li> </ul> <h3 id="v11-rbms">V11: RBMs</h3> <p>Slide name: V11_2015-05-27_RBMs</p> <dl> <dt><dfn>Hopfield-Netz</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Hopfield-Netz">Wikipedia</a>)</dt> <dd>Ein Hopfield-Netz besteht nur aus einer Schicht von McCulloch-Pitts Neuronen. Jedes Neuron ist mit jedem anderen Neuron (also nicht sich selbst) und allen Inputs verbunden. Die Schicht funktioniert gleichzeitig als Ein- und Ausgabeschicht.</dd> <dt><dfn>Boltzmann-Maschine</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Boltzmann-Maschine">Wikipedia</a>)</dt> <dd>Boltzmann-Maschinen sind stochastische neuronale Netzwerke, welche duch belibige ungerichtete Graphen repräsentiert werden können. Die neuronen sind binär; sie feuern also entweder oder nicht. Es gibt insbesondere keine Unterschiede in der Stärke mit der sie feuern.</dd> <dt><dfn>Restricted Boltzmann machine</dfn> (<dfn>RBM</dfn>, vgl. <a href="https://en.wikipedia.org/wiki/Restricted_Boltzmann_machine">Wikipedia</a>)</dt> <dd>Im Gegensatz zur Boltzmann-Maschine muss die Restricted Boltzmann-Machine (RBM) aus einem bipartitem Graph bestehen. Dies erlaubt ein effizienteres Trainingsverfahren.</dd> <dt><dfn>Simulated annealing</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Simulated_annealing">Wikipedia</a>)</dt> <dd>Simulated annealing ist ein heuristisches Optimierungsverfahren. Sei \(D\) ein Wertebereich einer Funktion \(f: D \rightarrow \mathbb{R}\) und \(U: D \rightarrow \mathcal{P}(D)\) eine Funktion, welche die Umgebung eines Punktes angibt. Sei \(T: \mathbb{N}_0 \rightarrow \mathbb{R}_{&gt; 0}\) die Temperatur zum Zeitpunkt \(t \in \mathbb{N}_0\). Gesucht ist \(\text{arg min}_{x \in D} f(x)\). Wähle zum Zeitpunkt \(t=0\) einen zufälligen Startwert \(x \in D\). Gehe nun iterativ vor und jeweils einen Zeitschritt weiter: Nehme einen Punkt aus der Umgebung \(y \in U(x)\). Wenn \(f(y) \leq f(x)\), dann überschreibe \(x \leftarrow y\). Falls nicht, dann überschreibe es mit der Wahrscheinlichkeit \(\exp \left (-\frac{f(y)-f(x)}{T(t)} \right )\). Speichere in jedem Schritt den bisher besten Wert. </dd> </dl> <p>Anwendungen:</p> <ul> <li>RBMs: <ul> <li>Collaborative Filtering: User-rating prediction for movie database. The problem is that not every user has rated all movies.</li> </ul> </li> </ul> <p>Fragen:</p> <ul> <li>Hopfield-Netze: <ul> <li>Wie trainiert man sie?</li> <li>Wo werden / wurden sie benutzt?</li> </ul> </li> </ul> <p>Siehe auch:</p> <ul> <li>Deeplearning.net: <a href="http://deeplearning.net/tutorial/rbm.html">Restricted Boltzmann Machines (RBM)</a></li> <li>Wikipedia: <a href="https://en.wikipedia.org/wiki/Restricted_Boltzmann_machine">Restricted Boltzmann machine</a></li> </ul> <h3 id="v12-rnns">V12: RNNs</h3> <p>Slide name: <code>V12_2015-06-02_RNNs.pdf</code></p> <dl> <dt><dfn>Elman-Netz</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Elman-Netz">Wikipedia</a>)</dt> <dd>Ein rekurrentes neuronales Netzwerk, bei dem die Ausgabe eines hidden layers im nächsten Zeitschritt als Eingabe verwendet wird.</dd> <dt><dfn>Jordan-Netz</dfn> (vgl. <a href="https://de.wikipedia.org/wiki/Jordan-Netz">Wikipedia</a>)</dt> <dd>Ein rekurrentes neuronales Netzwerk, bei dem die Ausgabe der Ausgabeschicht im nächsten Zeitschritt als Eingabe verwendet wird.</dd> <dt><dfn>Backpropagation through Time</dfn> (<dfn>BPTT</dfn>)</dt> <dd>Ein Trainingsalgorithmus für rekurrente neuronale Netze, bei dem das Netz "ausgerollt" wird. Das rekurrente Netz wird also als unendlich großes nicht-rekurrentes Netz behandelt.</dd> <dt><dfn>Vanishing gradient problem</dfn> (vgl. <a href="https://en.wikipedia.org/wiki/Vanishing_gradient_problem">Wikipedia</a>)</dt> <dd>Das Problem des verschwindenden Gradienten ist eine Herausforderung im Kontext neuronaler Netze, welche mit Backpropagation trainiert werden. Insbesondere bei sehr tiefen oder rekurrenten Netzen kann es passieren, dass der Gradient bei den ersten Schichten sehr niedrig ist, sodass das Netz sehr langsam lernt. Aufgrund numerischer Ungenauigkeit kann dies sogar dazu führen, dass das Netz in den ersten Schichten nicht lernen kann.</dd> <dt><a href="https://en.wikipedia.org/wiki/Long_short-term_memory"><dfn>Long short-term memory</dfn></a> (vgl. <dfn>LSTM</dfn>)</dt> <dd>Ein LSTM ist ein Typ eines neuronalen Netzwerks. Das besondere an LSTM Netzen sind "intelligente" Neuronen, welche über Gates bestimmen ob ein Wert gespeichert wird und wie lange.</dd> </dl> <p>Siehe auch:</p> <ul> <li><a href="http://karpathy.github.io/2015/05/21/rnn-effectiveness/">The Unreasonable Effectiveness of Recurrent Neural Networks</a></li> <li><a href="http://www.cs.toronto.edu/~ilya/fourth.cgi?prefix=E%3D&amp;numChars=300">Char-Predictor online Demo</a></li> <li><a href="http://www.wildml.com/2015/09/recurrent-neural-networks-tutorial-part-1-introduction-to-rnns/">Recurrent Neural Networks Tutorial, Part 1 – Introduction to RNNs</a></li> <li>YouTube: <a href="https://www.youtube.com/watch?v=SKMpmAOUa2Q">Vanishing Gradient</a> (5:24 min)</li> <li><a href="http://datascience.stackexchange.com/q/9510/8820">Where does the name ‘LSTM’ come from?</a></li> </ul> <h3 id="v13-nnlearning-tricks">V13: NNlearning-tricks</h3> <p>Slide name: <code>V13_2015-06-09_NNlearning-tricks.pdf</code></p> <dl> <dt><dfn>Momentum</dfn></dt> <dd>In der Update-Regel \(\Delta w_{ij}^* (t+1) = \Delta w_{ij} (t+1) + \alpha \Delta w_{ij}(t)\) wird der Term \(\Delta w_{ij}(t)\) als <i>Momentum</i> bezeichnet. Der Skalar \(\alpha \in [0, 1]\) gewichtet diesen und ist ein Hyperparameter.</dd> <dt><dfn>Quickprop</dfn> (<a href="https://en.wikipedia.org/wiki/Quickprop">Wikipedia</a>)</dt> <dd>Quickprop ist ein Trainingsverfahren für neuronale Netze. TODO: Wie funktioniert es?</dd> <dt><dfn>Weight Decay</dfn></dt> <dd>Passe die Fehlerfunktion an: \(E = MSE + \lambda \sum_{i,j} w_{ij}^2\)</dd> <dt><dfn>Weight Elimination</dfn></dt> <dd>Passe die Fehlerfunktion an: \(E = MSE + \lambda \sum_{i,j} \frac{w_{ij}^2}{1+w_{ij}^2}\)</dd> <dt><dfn>Optimal Brain Damage</dfn></dt> <dd>Optimal Brain Damage entfernt nach dem Training Verbindungen die sehr kleine \(|w_{ij}|\) haben. Besser: Entferne Verbindungen, die geringen Einfluss auf die Fehlerfunktion haben.</dd> <dt><dfn>Cascade Correlation Architecture</dfn> (siehe Fahlman und Lebiere: <a href="http://papers.nips.cc/paper/207-the-cascade-correlation-learning-architecture.pdf">The Cascade-Correlation Learning Architecture</a>)</dt> <dd>Die Cascade Correlation Architecture wird Schritt für Schritt aufgebaut. Sie ist keine typische Multilayer-Architektur.</dd> </dl> <p>Speed-ups sind möglich durch:</p> <ul> <li>Momentum</li> <li>Überspringen von bereits gut gelernten Beispielen</li> <li>Dynamische Anpassung der Lernrate <code>$\eta$</code></li> <li>Quickprop</li> <li>Gute Initialisierung</li> </ul> <p>Lernen kann getweakt werden:</p> <ul> <li>Fehlerfunktion anpassen <ul> <li><abbr title="Mean Squared Error">MSE</abbr></li> <li>Cross-Entropy</li> <li><abbr title="Classification Figure of Merit">CFM</abbr></li> </ul> </li> <li>Overfitting verhindern <ul> <li>Weight decay</li> <li>Weight elimination</li> <li>Optimal Brain Damage</li> <li>Optimal Brain Surgeon</li> </ul> </li> <li>Schrittweise Netzkonstruktion <ul> <li>Cascade Correlation</li> <li>Meiosis Netzwerke (siehe Stephen Jose Hanson: <a href="http://papers.nips.cc/paper/227-meiosis-networks.pdf">Meiosis Networks </a>)</li> <li><abbr title="Automativ Structure Optimalization">ASO</abbr>: TODO - wie funktioniert das?</li> </ul> </li> </ul> <p>Fragen:</p> <ul> <li>Folie 19: Was passiert hier? (TODO)</li> </ul> <h3 id="v14-dnn-cv">V14: DNN CV</h3> <p>Slide name: <code>V14_2015-06-10_DNN_CV .pdf</code></p> <dl> <dt><dfn>SIFT</dfn> (<dfn>Scale-invariant feature transform</dfn>, siehe <a href="https://en.wikipedia.org/wiki/Scale-invariant_feature_transform">Wikipedia</a>)</dt> <dd>Unter SIFT versteht man bestimmte Features in der Bildverarbeitung, welche invariant unter skalierung sind.</dd> <dt><dfn>Texton</dfn> (siehe <a href="https://en.wikipedia.org/wiki/Texton">Wikipedia</a> und <a href="http://vcla.stat.ucla.edu/old/Chengen_Research/texton.htm">UCLA</a>)</dt> <dd>Unter einem Texton versteht man grundlegende, kleine Features eines Bildes. Diese Bilden die kleinsten als unterschiedlich wahrnehmbaren Einheiten.</dd> <dt><dfn>Convolutional Neural Network</dfn> (<dfn>CNN</dfn>, siehe <a href="https://en.wikipedia.org/wiki/Convolutional_neural_network">Wikipedia</a>)</dt> <dd>Ein CNN ist ein Neuronales Netzwerk, welches mindestens eine Schicht hat, welche die Parameter eines Kernels für eine Faltung lernt.</dd> <dt><dfn>Feature Map</dfn></dt> <dd>Im Kontext von CNNs versteht man unter einer Feature-Map die Ausgabe eines Kernels in einem Convolutional Layer.</dd> </dl> <p>Facts:</p> <ul> <li>Pooling: Max, Mean, Probabilistic</li> </ul> <h3 id="v15-speech-independence">V15: Speech-Independence</h3> <p>Slide name: <code>V15_2015-06-17_Speech-Independence.pdf</code></p> <h2 id="visualisierung-von-netzen">Visualisierung von Netzen</h2> <p>Häufig wird die Architektur neuronaler Netze grafisch dargestellt. Dabei ist mir folgendes aufgefallen:</p> <ul> <li>Im Innenren von Neuronen wird die Aktivierungsfunktion “geplottet”. Das heißt bei der Sigmoidfunktion wird etwas S-Förmiges dargestellt, bei der sign-Funktion etwas eckiges, bei ReLU ein horizontaler Strich gefolgt von einem Strich im 45-Grad Winkel … (TODO: Beispiele aufzeichnen)</li> <li>Typischerweise ist der Input links (oder alternativ unten) und der Output rechts (oder alternativ oben)</li> </ul> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://ies.anthropomatik.kit.edu/lehre_mustererkennung.php">Vorlesungswebsite</a></li> <li><a href="https://github.com/thanhleha/NNPraktikum">NNPraktikum</a>: Toolkit für die Übungsblätter</li> <li>StackExchange <ul> <li>✓ <a href="http://stats.stackexchange.com/q/74082/25741">What is the difference in Bayesian estimate and maximum likelihood estimate?</a></li> <li>✓ <a href="http://datascience.stackexchange.com/q/9172/8820">Can k-means clustering get shells as clusters?</a></li> <li><a href="http://datascience.stackexchange.com/q/9177/8820">How is the Schwarz Criterion defined?</a></li> <li><a href="http://datascience.stackexchange.com/q/9195/8820">Are there studies which examine dropout vs other regularizations?</a></li> <li><a href="http://datascience.stackexchange.com/q/9175/8820">How do subsequent convolution layers work?</a></li> <li>✓ <a href="http://datascience.stackexchange.com/q/9212/8820">Is Maxout the same as max pooling?</a></li> <li><a href="http://robotics.stackexchange.com/q/8617/11257">What is \(\alpha \sin(\theta) + \beta \frac{d \theta}{d t}\) in the inverted pole problem?</a></li> <li>✓ <a href="http://datascience.stackexchange.com/q/9233/8820">(Why) do activation functions have to be monotonic?</a></li> <li><a href="http://datascience.stackexchange.com/q/9302/8820">The cross-entropy error function in neural networks</a></li> </ul> </li> <li><a href="http://imgur.com/a/Hqolp">Visualizing Optimization Algos</a></li> <li><a href="http://phiresky.github.io/kogsys-demos/neural-network/">Neural Network demo</a></li> <li><a href="https://github.com/Marvin182/NeuralNets">Skript von Marvin Ritter</a></li> <li><a href="//martin-thoma.com/machine-learning-1-course/">Machine Learning 1</a> und <a href="//martin-thoma.com/machine-learning-2-course/">Machine Learning 2</a> am KIT</li> <li>Coursera: <a href="https://class.coursera.org/neuralnets-2012-001/lecture">Neural Networks for Machine Learning</a> by Geoffrey Hinton</li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <p>Übungsblätter sind freiwillig.</p> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: nach Terminvereinbarung<br /> <strong>Ort</strong>: <a href="http://www.kithub.de/map/2210">Gebäude 50.20</a><br /> <strong>Übungsschein</strong>: gibt es nicht<br /> <strong>Bonuspunkte</strong>: gibt es nicht<br /> <strong>Erlaubte Hilfsmittel</strong>: keine</p> Mustererkennung - Klausur //martin-thoma.com/mustererkennung-klausur/ Mon, 27 Apr 2015 21:15:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/mustererkennung-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Mustererkennung&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://ies.anthropomatik.kit.edu/mitarbeiter.php?person=beyerer">Herrn Prof. Dr.-Ing. Jürgen Beyerer</a> im Sommersemester 2015 gehört und einige Abschnitte direkt aus den Folien übernommen.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="vorlesung">Vorlesung</h3> <table> <tr> <th>Datum</th> <th>Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>15.04.2015</td> <td><a href="https://ies.anthropomatik.kit.edu/ies/download/lehre/me/ME-Kap1_V33.pdf">Einleitung</a></td> <td>`$\hat{w}$` - das <code>^</code> bedeutet, dass die Klasse geschätzt ist.</td> </tr> <tr> <td>22.04.2015</td> <td><a href="https://ies.anthropomatik.kit.edu/ies/download/lehre/me/ME-Kap2_V85.pdf">Kapitel 2 - Merkmale</a>: 1-31?</td> <td>Welt; Domäne; Objekte; Klassen; Merkmalsraum; Merkmalsvektor; Klassifikation; Skalen (nominal, ordinal, intervall-, verhältnis- und absolutskaliert); Projektionen; <a href="https://de.wikipedia.org/wiki/Norm_(Mathematik)#Definition">Norm</a> (Minkowski, Euklidisch, Chebychev, Mahalanobis); <a href="https://de.wikipedia.org/wiki/Metrischer_Raum#Formale_Definition">Metrik</a> (Tanimoto)</td> </tr> <tr> <td>14.07.2015</td> <td><a href="http://ies.anthropomatik.kit.edu/ies/download/lehre/me/ME-Kap8_V25.pdf">Kapitel 8 - Klassifikatoren</a> (1-28), <a href="https://ies.anthropomatik.kit.edu/ies/download/lehre/me/ME-Kap9_V29.pdf">Kapitel 9</a>: 1-?</td> <td>Entscheidungsbäume, Grammatiken; Lernen nach Vapnik, VC-dimension, Kreuzvalidierung und Leave-One-Out, Boosting</td> </tr> </table> <h3 id="folien">Folien</h3> <h4 id="me-kap1v31pdf">ME-Kap1_V31.pdf</h4> <p><strong>Einleitendes Kapitel</strong> welches erklärt, was Klassifikation ist.</p> <ul> <li>Beispiele für Klassifikation: Blumen/Schmetterlinge in Arten; Schrauben in Schraubentypen; Schüttgut in Mineralien, Pflanzen, Glasscheiben, Diamante, …</li> <li>Formalismen <ul> <li>Domäne <code>$\Omega \subseteq $</code> Welt, Elemente der Domäne heißen Objekte, Objekte werden in paarweise disjunkte Äquivalenzklassen <code>$\omega_i$</code> gruppiert, sodass jedes Objekt genau eine Äquivalenzklasse hat.</li> <li>Man beobachtet / misst Eigenschaften realer Objekte. Dies kann als Funktion <strong>m</strong> aufgefasst werden, die von der Domäne in den Merkmalsraum abbildet. Optimalerweise ist diese Abbildung injektiv, bei ungünstig gewählten Merkmalen jedoch nicht. Klassifikatoren arbeiten auf dem Merkmalsraum und finden eine Partition des Merkmalsraumes in Klassen</li> </ul> </li> <li><strong>Muster</strong>: Gesamtheit der beobachteten / gemessenen Werte einer einzelnen Stichprobe (eines einzelnen Objekts).</li> <li><strong>Erkennung</strong>: (Wieder)erkennung von etwas, was bereits bekannt ist.</li> <li><strong>Merkmale</strong>: eruirbare, charakteristische Eigenschaften, die als Basis für die Untersuchung von Mustern dienen soll.</li> <li><strong>Mustererkennungsschritte</strong>: Sensierung ergibt Muster; Vorverarbeitung; Segmentierung; Merkmalsextraktion ergibt Merkmale; Klassifikation ergibt Äquivalenzklassen</li> <li><strong>Überwachtes lernen</strong>: Vorklassifizierte Beispiele sowie die Klassenstruktur sind gegeben; eventuell auch Auftrittswahrscheinlichkeiten <code>$P(\omega_i)$</code> der Klassen</li> <li>Gesamtstichprobe wird in die disjunkten Mengen Lernstrichprobe, Validierungsstichprobe und Teststichprobe zerlegt.</li> </ul> <h4 id="me-kap2v84pdf">ME-Kap2_V84.pdf</h4> <p>In diesem Foliensatz geht es um <strong>Merkmale</strong> und ihre Eigenschaften.</p> <table border="1"> <tr> <th rowspan="3">&nbsp;</th> <th colspan="5">Skala</th> </tr> <tr> <th colspan="2">qualitativ</th> <th colspan="3">quantitativ (metrisch)</th> </tr> <tr> <th>Nominal-</th> <th>Ordinal-</th> <th>Intervall-</th> <th>Verh&auml;ltnis-</th> <th>Absolut</th> </tr> <tr> <th>Empirische Relation</th> <td>~ &Auml;quivalenz</td> <td>~ &Auml;quivalenz<br />Ordnung</td> <td>~ &Auml;quivalenz<br />Ordnung<br />Emp. Addition</td> <td>~ &Auml;quivalenz<br />Ordnung<br />Emp. Addition<br />Emp. Multipliation</td> <td>~ &Auml;quivalenz<br />Ordnung<br />Emp. Addition<br />Emp. Multipliation</td> </tr> <tr> <th>Zul&auml;ssige Transformationen</th> <td>m' = f(m)<br />f bijektiv</td> <td>m' = f(m)<br />f streng monoton</td> <td>m' = am+b<br />mit a&gt;0</td> <td>m' = am<br />mit a&gt;0</td> <td>m' = m</td> </tr> <tr> <th>Beispiele zugeh&ouml;rige Merkmale</th> <td>Telefonnummern, Kfz-Kennz., Typen, PLZ, Geschlecht</td> <td>G&uuml;teklassen, H&auml;rtegrad, Windst&auml;rke</td> <td>Temp. in &deg;C, &deg;F, Kalenderzeit, geographische H&ouml;he</td> <td>Masse, L&auml;nge, el. Strom</td> <td>Quantenzahlen, Teilchenanzahl, Fehlerzahl</td> </tr> <tr> <th>Werte von m</th> <td>Zahlen, Namen, Symbole</td> <td>in der Regel nat&uuml;rliche Zahlen</td> <td>in der Regel reele Zahlen</td> <td>in der Regel reele Zahlen &gt; 0</td> <td>in der Regel nat&uuml;rliche Zahlen</td> </tr> </table> <p>Der Merkmalsraum ist häufig ein <code>$\mathbb{R}^n$</code> mit <code>$n&gt;3$</code>. Er kann auf vorhandene Strukturen analysiert werden, indem er auf einen 2- oder 3-dimensionalen unterraum projeziert wird. Dies kann bei einfachen Projektionen jedoch nicht erfolgreich sein, wenn beispielsweise zwei Klassen Schalenförmig um den Urspruch angeordnet sind.</p> <p>Um Stichproben im Merkmalsraum zu vergleichen können Metriken benutzt werden. Eine <a href="https://de.wikipedia.org/wiki/Metrischer_Raum#Formale_Definition">Metrik</a> ist eine Abbildung <code>$d(m_1, m_2)$</code>, für die gilt:</p> <ul> <li>Positive Definitheit: <code>$d(m_1, m_2) \geq 0$</code> und <code>$d(m_1, m_2) = 0 \Leftrightarrow m_1 = m_2$</code>,</li> <li>Symmetrie: <code>$d(m_1, m_2) = d(m_2, m_1)$</code>,</li> <li>Dreiecksungleichung: <code>$d(m_1, m_2) \leq d(m_1, m_3) + d(m_3, m_2)$</code></li> </ul> <p>Metriken können durch <a href="https://de.wikipedia.org/wiki/Norm_(Mathematik)#Definition">Normen</a> erzeugt werden, indem <code>$d(m_1, m_2) := \|m_1 - m_2\|$</code> definiert wird. Eine Norm ist eine Abbildung <code>$\| \cdot \|: V \rightarrow \mathbb{R}_0^+, x \mapsto \|x\|$</code> für die gilt:</p> <ul> <li>Definitheit: <code>$\|x\| = 0 \Rightarrow x = 0$</code></li> <li>Absolute Homogenität: <code>$\|\alpha \cdot x \| = \alpha \cdot \| x \|$</code></li> <li>Dreiecksungleichung: <code>$\|x+y\| \leq \|x\| + \|y\|$</code></li> </ul> <p>Typische Normen sind die <a href="https://de.wikipedia.org/wiki/Euklidische_Norm">euklidische Norm</a> und die Mahalanobis Norm <code>$\|m\| := \sqrt{m^T A m}$</code> mit <code>$A$</code> positiv definit.</p> <p><strong>Hauptkomponentenanalyse</strong> (HKA, engl. PCA)</p> <ol> <li>Finde <code>$m_0$</code>, sodass <code>$J_0(m) := \sum_{k=1}^N \|m - m_k\|^2$</code> minimal ist, also <code>$m_0 = \frac{1}{N} \sum_{k=1}^N m_k$</code></li> <li>Finde Gerade <code>$h: m = \bar{m} + ae$</code>, welche die Punkte optimal repräsentiert. <ol> <li>Finden der <code>$a_k$</code> (TODO: Was ist das?) Fehlermaß <code>$J_1(a_1, \dots, a_N, e) = \sum_{k=1}^N \|\bar{m} + a_k e - m_k \|^2$</code>. Ergibt: <code>$a_k = e^T (m_k - \bar{m})$</code></li> <li>Berechnung des optimalen Richtungsvektors Streumatrix <code>$S := \sum_{k=1}^N (m_k - \bar{m}) (m_k - \bar{m})^T$</code></li> </ol> </li> <li>Finden eines affinen <code>$d'$</code>-dimensionalen Unterraumes des Merkmalsraumes, welcher die Daten <code>$D$</code> mit minimalen quadratischem Fehler repräsentiert.</li> </ol> <p>Siehe <a href="https://gist.github.com/MartinThoma/09799f5d143c09399eed">gist</a> für eine kurze Python-Implementierung. Keine Garantie für die Korrektheit!</p> <ul> <li>Kernelized PCA</li> <li>Independent Component Analysis (ICA)</li> <li>Multiple Discriminant Analysis (MDA)</li> </ul> <h4 id="me-kap3v52pdf">ME-Kap3_V52.pdf</h4> <p><strong>Bayessche Klassifikatoren</strong> wählen die Klasse aus, die die größte Wahrscheinlichkeit besitzt. Dazu verfolgt man den Ansatz</p> <p><code> $$P(\omega|m) = \frac{p(m|\omega) \cdot P(\omega)}{p(m)}$$</code></p> <p>Dabei wird <code>$P(\omega|m)$</code> die <em>A Posteriori Wahrscheinlichkeitsverteilung</em> und <code>$P(\omega)$</code> die <em>A Priori Wahrscheinlichkeitsverteilung</em> genannt.</p> <h4 id="me-kap4v33pdf">ME-Kap4_V33.pdf</h4> <p><strong>Parameterschätzung</strong> kann entweder mit der Likelihood-Methodik oder mit der Bayesschen Methodik durchgeführt werden. Die Idee der Likelihood-Methodik ist es, den Parameter <code>$\theta$</code> als unbekannte konstante (d.h. nicht-stochastische) Größe anzusehen. Man wählt <code>$\theta$</code> also so, dass die Wahrscheinlichkeit der Beobachtungen gegeben <code>$\theta$</code> maximiert wird.</p> <p>Die Bayessche Methodik geht dagegen davon aus, dass <code>$\theta$</code> auch eine Zufallsvariable ist und über eine Wahrscheinlichkeitsverteilung beschrieben werden kann.</p> <p>Schätzer können verschiedene Qualitätskriterien erfüllen, z.B. <a href="https://de.wikipedia.org/wiki/Erwartungstreue">Erwartungstreue</a> oder <a href="https://de.wikipedia.org/wiki/Konsistenz_(Statistik)">Konsistenz</a>.</p> <p>Bei der Parameterschätzung können folgende Fehler passieren:</p> <ul> <li>Bayesscher Fehler: (TODO: Was ist das?)</li> <li>Modellfehler: Unpassendes Modell gewählt (Falsche Verteilungsannahme?)</li> <li>Schätzfehler: Zu wenige Daten um Parameter korrekt zu bestimmen</li> </ul> <h4 id="me-kap5v31pdf">ME-Kap5_V31.pdf</h4> <p><strong>Parameterfreie Methoden</strong> heißen “parameterfrei”, weil sie keine konkrete Wahrscheinlichkeitsverteilung parametrisieren und den Parameter schätzen. Die Parameterfreien Methoden können sehr wohl Parameter benutzen. Beispiele sind:</p> <ul> <li><a href="https://de.wikipedia.org/wiki/Kerndichtesch%C3%A4tzer">Parzen Window</a></li> <li><a href="https://de.wikipedia.org/wiki/N%C3%A4chste-Nachbarn-Klassifikation">Nächste Nachbarn</a></li> </ul> <h4 id="me-kap6v18pdf">ME-Kap6_V18.pdf</h4> <p><strong>Allgemeine Problemstellungen</strong>:</p> <ul> <li>Dimension des Merkmalsraumes</li> <li>Overfitting</li> </ul> <h4 id="me-kap7v54pdf">ME-Kap7_V54.pdf</h4> <p><strong>Spezielle Klassifikatoren</strong>:</p> <ul> <li>Lineare Diskriminanzfunktionen: Linear bezieht sich hier auf die Kombination der Merkmale. Man kann allerdings Merkmale wählen, die z.B. das quadrat eines gemessenen wertes sind.</li> <li>Perzeptron</li> <li>Lineare Regression</li> <li>Künstliche Neuronale Netze</li> <li>Support Vector Machines (SVMs)</li> <li>Matched Filter</li> <li>HMMs (Sequenzen)</li> <li>Klassifikation mit Rückweisung (Maximum / Minimum / Differenz / Abstand)</li> </ul> <h4 id="me-kap8v21pdf">ME-Kap8_V21.pdf</h4> <p><strong>Klassifikation bei nominalen Merkmalen</strong>:</p> <ul> <li>Entscheidungsbäume</li> <li>String-Verfahren</li> <li>Grammatiken</li> </ul> <h4 id="me-kap9v27pdf">ME-Kap9_V27.pdf</h4> <p><strong>Klassifikatorunabhängige Prinzipien</strong>:</p> <ul> <li>Generalisierung / Generalisierungsfähigkeit</li> <li>VC-Konfidenz / VC-Dimension</li> <li>Structural Risc Minimization</li> <li><a href="https://de.wikipedia.org/wiki/Kreuzvalidierungsverfahren">Kreuzvalidierungsverfahren</a> / Leave-one-out</li> <li>Boosting</li> </ul> <h3 id="prfungsfragen">Prüfungsfragen</h3> <ul> <li>Warum ist ein hochdimensionaler Merkmalsraum schlecht (<a href="https://en.wikipedia.org/wiki/Curse_of_dimensionality">curse of dimensionality</a>)? <ul> <li>Je nach Klassifikator, viele zu lernende Parameter</li> <li>Daten haben einen sehr hohen Abstand zueinander → Gefahr des Overfittings</li> </ul> </li> <li>Wie kann man die Dimension des Merkmalsraumes reduzieren? → Merkmalsauswahl, suboptimales iteratives Verfahren, HKA (Varianzen maximieren), MDA (Klassentrennbarkeit maximieren), ICA</li> <li>Wie viele Möglichkeiten gibt es 5 Merkmale aus 10 auszuwählen? → <a href="https://de.wikipedia.org/wiki/Binomialkoeffizient">Binomialkoeffizient</a></li> <li>Was ist Overfitting? (Zu starke Anpassung des Klassifizierers an die Lerndaten; geringe Generalisierungsfähgikeit)</li> <li>Welche Probleme gibt es, wenn man Länge, Masse und Temperatur als Merkmale hat? <ul> <li>Unterschiedliche Einheiten (→ Entdimensionalisieren)</li> <li>Unterschiedliche Skalen (→ Teilen durch Varianz oder durch Wertebereich)</li> <li>Unterschiedliche Wertebereiche (→ Durchschnitt abziehen)</li> </ul> </li> <li>Wie funktioniert MDA? → Sie maximiert <code>$J(w) = \frac{|m'_1 - m'_2|^2}{s'_1^2 - s'_2^2}$</code> (im 2-Klassen Fall, wobei <code>$w$</code> die Ebene ist, auf die projeziert wird)</li> <li>Wie unterscheidet sich PCA/MDA von dem suboptimalen Algorithmus zur Merkmalsauswahl? → PCA/MDA sind Klassifikatorunabhängig, aber der suboptimale Algorithmus benötigt bereits einen Klassifikator.</li> <li>Wie lautet die Fundamentalformel der Bayesschen Klassifikation? → <code>$P(A|B) = \frac{P(A)\, P(B | A)}{P(B)}$</code> (wobei üblicherweise B das Merkmal ist und A die Klasse)</li> <li>Wie lautet die Hauptformel der PCA? <code>$m' = A^T \cdot (m - \bar{m})$</code>, wobei <code>$A$</code> die Basiswechselmatrix ist.</li> <li>Wie kann man invariante Merkmale erzeugen? → Integration über eine Transformationsgruppe, Differentielle Methode, Normalisierung</li> <li>Wie kann man normalisieren? → Fourierdeskriptoren kann man invariant bzgl. Translation und Rotation und radialer Streckung (Skalierung) machen</li> <li>Wie lauten die Prinzipien (A) - (E) der SVMs? <ul> <li>(A) Lineare Trennung mit maximalen Abstand der Trennebenen zu den nächstgelegenen Stichproben (Support Vektoren)</li> <li>(B) Duale Formulierung des linearen Klassifikators. (vgl. <a href="https://de.wikipedia.org/wiki/Support_Vector_Machine#Duales_Problem">Wiki</a>, <code>$k(m) = w^T m + b = \langle w, m \rangle + b = \sum_{j=1}^N \alpha_j z_j \langle m_j, m \rangle + b$</code>)</li> <li>(C) Nichtlineare Abbildung der primären Merkmale in einen hochdimensionalen Merkmalsraum <code>$\Phi$</code></li> <li>(D) Implizite Nutzung des unter Umständen <code>$\infty$</code>-dimensionalen Eigenfunktionsraumes einer sog. Kernfunktion <code>$K$</code> als transformierten Merkmalsraum <code>$\Phi$</code>. Dabei müssen die transformierten Merkmale nicht explizit berechnet werden und der Klassifikator hat trotz der hohen Dimension von <code>$\Phi$</code> nur eine niedrige Zahl von freien Parametern (Kernel-Trick).</li> <li>(E) Relaxation der Forderung nach linearer Trennbarkeit durch Einführung von Schlupfvariablen (slack variables).</li> </ul> </li> <li>Wie lautet die Dichtefunktion der <a href="https://de.wikipedia.org/wiki/Mehrdimensionale_Normalverteilung"><code>$d$</code>-dimensionale Gaußverteilung</a>? <code>$f_X(x) = \frac{1}{\sqrt{(2\pi \det{\Sigma})}} \exp(-\frac{1}{2}(x-\mu)^T \Sigma^{-1} (x-\mu))$</code></li> <li>Wie lautet Mercers Theorem? → <a href="https://de.wikipedia.org/wiki/Satz_von_Mercer">wiki</a></li> <li>Wie ist die <a href="https://de.wikipedia.org/wiki/Kullback-Leibler-Divergenz">Kullback-Leibler-Divergenz</a> defininiert?</li> </ul> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://ies.anthropomatik.kit.edu/lehre_mustererkennung.php">Vorlesungswebsite</a>: Ist passwortgeschützt. Das Passwort (das ausnahmsweise mal nicht zu erraten ist) kann ich hier natürlich nicht schreiben. Aber der Benutzername ist <code>asbstudent</code>.</li> <li>SVMs <ul> <li><a href="http://stats.stackexchange.com/q/19181/25741">Why bother with the dual problem when fitting SVM?</a></li> <li><a href="http://research.microsoft.com/pubs/67119/svmtutorial.pdf">A Tutorial on Support Vector Machines for Pattern Recognition</a></li> </ul> </li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <p>Es gibt keine Übungsblätter, keine Übungen, keine Tutorien und keine Bonuspunkte.</p> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Donnerstag, der 10.09.2015 von 11:00-13:00 Uhr (Quelle: Wurde in der Vorlesung vom 22.04.2015 gesagt)<br /> <strong>Ort</strong>: <a href="http://www.kithub.de/map/2287">Gerthsen-Hörsal</a><br /> <strong>Punkte</strong>: 90<br /> <strong>Zeit</strong>: 90 min<br /> <strong>Punkteverteilung</strong>: ?<br /></p> <ul> <li>ab 60.5: 1.7</li> </ul> <p><strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: gibt es nicht<br /> <strong>Bonuspunkte</strong>: gibt es nicht<br /> <strong>Ergebnisse</strong>: Am 30.09.2015 war die (vorläufige) Note im Notenauszug<br /> <strong>Einsicht</strong>: Montag 12.10.2015, 9:00-15:00 Uhr im <a href="https://www.kithub.de/map/2577">Geb. 50.21</a>, Raum 015.1<br /> <strong>Erlaubte Hilfsmittel</strong>: keine</p> <h2 id="notenverteilung">Notenverteilung</h2> <p>Wenn ihr mir schreibt was ihr habt, kann ich das updaten:</p> <ul> <li>1,3: min 1</li> <li>2,0: min 1</li> </ul> Lasagne for Python Newbies //martin-thoma.com/lasagne-for-python-newbies/ Fri, 17 Apr 2015 19:26:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/lasagne-for-python-newbies <p>Lasagne is a Python package for training neural networks. The nice thing about Lasagne is that it is possible to write Python code and execute the training on nVidea GPUs with automatically generated CUDA code.</p> <p>However, installing Lasagne is not that easy. Especially if you are not familiar with Python. This article aims to guide you through the installation process.</p> <h2 id="python">Python</h2> <p>Ubuntu-based systems will have Python installed, but I’m not too sure about pip. You can get it with</p> <pre><code>$ sudo apt-get install python-pip </code></pre> <p>Make sure you have Python and <code>pip</code>, the standard Python package installer. Type the following commands to check if you have both:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ python --version Python 2.7.8 $ pip --version pip 6.1.1 from /usr/local/lib/python2.7/dist-packages (python 2.7) </pre></div> </div> </div> <h2 id="sklearn">sklearn</h2> <p><a href="http://scikit-learn.org/stable/">sklearn</a> is a nice package for machine learning. You can install it with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pip install scikit-learn </pre></div> </div> </div> <p>(When I write commands like this you either have to execute <code>sudo pip install scikit-learn</code> or <code>pip install scikit-learn --user</code>).</p> <p>This should work without problems.</p> <p>Each classifier has a <code>fit</code> method and a <code>predict</code> method. See <a href="http://scikit-learn.org/stable/auto_examples/svm/plot_iris.html">iris example</a> to get a feeling how to use it. It provides a lot of useful functions like <a href="http://scikit-learn.org/stable/modules/generated/sklearn.cross_validation.train_test_split.html"><code>train_test_split</code></a> and has an awesome documentation.</p> <p>You don’t need this for Lasagne, but it might be good to use sklearn and Lasagne in combination.</p> <h2 id="graphics-drivers-and-cuda">Graphics drivers and CUDA</h2> <p>Make sure CUDA runs on your system by the following commands. If it doesn’t run, you could try the following guides:</p> <ul> <li><a href="http://askubuntu.com/q/451672/10425">Installing and testing CUDA in Ubuntu 14.04</a></li> <li><a href="http://www.r-tutor.com/gpu-computing/cuda-installation/cuda6.5-ubuntu">Installing CUDA Toolkit 6.5 on Ubuntu 14.04 Linux</a></li> <li><a href="http://docs.nvidia.com/cuda/cuda-getting-started-guide-for-linux/#axzz3XaMVcNwV">NVIDIA CUDA Getting Started Guide for Linux</a></li> </ul> <p>Run</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ nvidia-smi -L GPU 0: GeForce GTX TITAN Black (UUID: GPU-abcdef12-abcd-1234-1234-01234567890a) $ nvcc --version nvcc: NVIDIA (R) Cuda compiler driver Copyright (c) 2005-2013 NVIDIA Corporation Built on Thu_Mar_13_11:58:58_PDT_2014 Cuda compilation tools, release 6.0, V6.0.1 $ nvidia-smi -a ==============NVSMI LOG============== Timestamp : Fri Apr 17 18:44:41 2015 Driver Version : 331.79 Attached GPUs : 1 GPU 0000:01:00.0 Product Name : GeForce GTX TITAN Black Display Mode : N/A Display Active : N/A Persistence Mode : Disabled Accounting Mode : N/A Accounting Mode Buffer Size : N/A Driver Model Current : N/A Pending : N/A Serial Number : N/A GPU UUID : GPU-fcff168f-a045-2f95-7a4f-8e1cf26a24eb Minor Number : 0 VBIOS Version : 80.80.4E.00.01 Inforom Version Image Version : N/A OEM Object : N/A ECC Object : N/A Power Management Object : N/A GPU Operation Mode Current : N/A Pending : N/A PCI Bus : 0x01 Device : 0x00 Domain : 0x0000 Device Id : 0x100C10DE Bus Id : 0000:01:00.0 Sub System Id : 0x106610DE GPU Link Info PCIe Generation Max : N/A Current : N/A Link Width Max : N/A Current : N/A Bridge Chip Type : N/A Firmware : N/A Fan Speed : 26 % Performance State : N/A Clocks Throttle Reasons : N/A FB Memory Usage Total : 6143 MiB Used : 39 MiB Free : 6104 MiB BAR1 Memory Usage Total : N/A Used : N/A Free : N/A Compute Mode : Default Utilization Gpu : N/A Memory : N/A Ecc Mode Current : N/A Pending : N/A ECC Errors Volatile Single Bit Device Memory : N/A Register File : N/A L1 Cache : N/A L2 Cache : N/A Texture Memory : N/A Total : N/A Double Bit Device Memory : N/A Register File : N/A L1 Cache : N/A L2 Cache : N/A Texture Memory : N/A Total : N/A Aggregate Single Bit Device Memory : N/A Register File : N/A L1 Cache : N/A L2 Cache : N/A Texture Memory : N/A Total : N/A Double Bit Device Memory : N/A Register File : N/A L1 Cache : N/A L2 Cache : N/A Texture Memory : N/A Total : N/A Retired Pages Single Bit ECC : N/A Double Bit ECC : N/A Pending : N/A Temperature Gpu : 29 C Power Readings Power Management : N/A Power Draw : N/A Power Limit : N/A Default Power Limit : N/A Enforced Power Limit : N/A Min Power Limit : N/A Max Power Limit : N/A Clocks Graphics : N/A SM : N/A Memory : N/A Applications Clocks Graphics : N/A Memory : N/A Default Applications Clocks Graphics : N/A Memory : N/A Max Clocks Graphics : N/A SM : N/A Memory : N/A Compute Processes : N/A </pre></div> </div> </div> <p>to see if CUDA was installed correctly.</p> <h2 id="theano">Theano</h2> <p>The installation of Theano is a bit tricky (see <a href="http://deeplearning.net/software/theano/install.html">official page</a>). I don’t remember if I installed additional packages, but try</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo -H pip install theano </pre></div> </div> </div> <p>Make sure that your <code>~/.theanorc</code> exists and looks like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[global] device=gpu floatX=float32 </pre></div> </div> </div> <p>Note that <code>float32</code> is required, even if you have a 64bit system.</p> <p>To test your installation, save the following as <code>theanotest.py</code> and execute it with <code>python theanotest.py</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">theano</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">function</span>, <span style="color:#B44;font-weight:bold">config</span>, <span style="color:#B44;font-weight:bold">shared</span>, <span style="color:#B44;font-weight:bold">sandbox</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">theano.tensor</span> <span style="color:#080;font-weight:bold">as</span> T <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">time</span> vlen = <span style="color:#00D">10</span> * <span style="color:#00D">30</span> * <span style="color:#00D">768</span> <span style="color:#777"># 10 x #cores x # threads per core</span> iters = <span style="color:#00D">1000</span> rng = numpy.random.RandomState(<span style="color:#00D">22</span>) x = shared(numpy.asarray(rng.rand(vlen), config.floatX)) f = function([], T.exp(x)) <span style="color:#080;font-weight:bold">print</span> f.maker.fgraph.toposort() t0 = time.time() <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">xrange</span>(iters): r = f() t1 = time.time() <span style="color:#080;font-weight:bold">print</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Looping %d times took</span><span style="color:#710">'</span></span> % iters, t1 - t0, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">seconds</span><span style="color:#710">'</span></span> <span style="color:#080;font-weight:bold">print</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Result is</span><span style="color:#710">'</span></span>, r <span style="color:#080;font-weight:bold">if</span> numpy.any([<span style="color:#369;font-weight:bold">isinstance</span>(x.op, T.Elemwise) <span style="color:#080;font-weight:bold">for</span> x <span style="color:#080;font-weight:bold">in</span> f.maker.fgraph.toposort()]): print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Used the cpu</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">else</span>: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Used the gpu</span><span style="color:#710">'</span></span>) </pre></div> </div> </div> <p>It should print the following (well, something similar):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Using gpu device 0: GeForce GTX TITAN Black [GpuElemwise{exp,no_inplace}(&lt;CudaNdarrayType(float32, vector)&gt;), HostFromGpu(GpuElemwise{exp,no_inplace}.0)] Looping 1000 times took 0.38205909729 seconds Result is [ 1.23178029 1.61879349 1.52278066 ..., 2.20771813 2.29967761 1.62323296] Used the gpu </pre></div> </div> </div> <p>Especially “used the gpu” is important. Theano code work on both, CPU and GPU. If you have a GPU and it does not currently work on a task and it is configured correctly, then Theano should automatically use the GPU.</p> <p>(Don’t try to run two Theano scripts at a time … weird things could happen.)</p> <h2 id="lasagne">Lasagne</h2> <p>Lasagne is hosted at Github: <a href="https://github.com/Lasagne/Lasagne">https://github.com/Lasagne/Lasagne</a></p> <p>Currently, it is not on pip as Sander wants to wait until we get to version 1.0. So you have to install it manually:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ git clone https://github.com/Lasagne/Lasagne.git $ cd Lasagne Lasagne$ sudo -H python setup.py install </pre></div> </div> </div> <p>Now you can test if it worked by executing the MNIST example in Lasagne (<a href="http://yann.lecun.com/exdb/mnist/">MNIST</a> is a huge digit dataset). This might first take some time to download, but should then run quite fast. If your machine does not use the GPU it will take ages (e.g. on my laptop it takes about a minute for one epoch)</p> <pre><code>Lasagne/examples$ python mnist.py Loading data... Downloading MNIST dataset Building model and compiling functions... /usr/local/lib/python2.7/dist-packages/Lasagne-0.1dev-py2.7.egg/lasagne/init.py:30: UserWarning: The uniform initializer no longer uses Glorot et al.'s approach to determine the bounds, but defaults to the range (-0.01, 0.01) instead. Please use the new GlorotUniform initializer to get the old behavior. GlorotUniform is now the default for all layers. warnings.warn("The uniform initializer no longer uses Glorot et al.'s " /usr/local/lib/python2.7/dist-packages/Lasagne-0.1dev-py2.7.egg/lasagne/layers/helper.py:55: UserWarning: get_all_layers() has been changed to return layers in topological order. The former implementation is still available as get_all_layers_old(), but will be removed before the first release of Lasagne. To ignore this warning, use `warnings.filterwarnings('ignore', '.*topo.*')`. warnings.warn("get_all_layers() has been changed to return layers in " Starting training... Epoch 1 of 500 took 72.593s training loss: 1.330231 validation loss: 0.470251 validation accuracy: 87.54 %% </code></pre> <h2 id="nolearn">nolearn</h2> <p><a href="https://github.com/dnouri/nolearn">nolearn</a> is another Python package. It was created to make using Lasagne even simpler.</p> <p>You can install it via</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ git clone https://github.com/dnouri/nolearn.git $ cd nolearn $ python setup.py install --user </pre></div> </div> </div> <p>For example, the following code downloads the MNIST dataset, trains a model on it and evaluates the result for a single image:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">lasagne</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">lasagne</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">layers</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">lasagne.updates</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">nesterov_momentum</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">nolearn.lasagne</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">NeuralNet</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">sys</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">gzip</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">pickle</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy</span> PY2 = sys.version_info[<span style="color:#00D">0</span>] == <span style="color:#00D">2</span> <span style="color:#080;font-weight:bold">if</span> PY2: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">urllib</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">urlretrieve</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">pickle_load</span>(f, encoding): <span style="color:#080;font-weight:bold">return</span> pickle.load(f) <span style="color:#080;font-weight:bold">else</span>: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">urllib.request</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">urlretrieve</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">pickle_load</span>(f, encoding): <span style="color:#080;font-weight:bold">return</span> pickle.load(f, encoding=encoding) DATA_URL = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">http://deeplearning.net/data/mnist/mnist.pkl.gz</span><span style="color:#710">'</span></span> DATA_FILENAME = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mnist.pkl.gz</span><span style="color:#710">'</span></span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">_load_data</span>(url=DATA_URL, filename=DATA_FILENAME): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Load data from `url` and store the result in `filename`.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">if</span> <span style="color:#080;font-weight:bold">not</span> os.path.exists(filename): print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Downloading MNIST dataset</span><span style="color:#710">&quot;</span></span>) urlretrieve(url, filename) <span style="color:#080;font-weight:bold">with</span> gzip.open(filename, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rb</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> f: <span style="color:#080;font-weight:bold">return</span> pickle_load(f, encoding=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">latin-1</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">load_data</span>(): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Get data with labels, split into training, validation and test set.</span><span style="color:black">&quot;&quot;&quot;</span></span> data = _load_data() X_train, y_train = data[<span style="color:#00D">0</span>] X_valid, y_valid = data[<span style="color:#00D">1</span>] X_test, y_test = data[<span style="color:#00D">2</span>] y_train = numpy.asarray(y_train, dtype=numpy.int32) y_valid = numpy.asarray(y_valid, dtype=numpy.int32) y_test = numpy.asarray(y_test, dtype=numpy.int32) <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">dict</span>( X_train=X_train, y_train=y_train, X_valid=X_valid, y_valid=y_valid, X_test=X_test, y_test=y_test, num_examples_train=X_train.shape[<span style="color:#00D">0</span>], num_examples_valid=X_valid.shape[<span style="color:#00D">0</span>], num_examples_test=X_test.shape[<span style="color:#00D">0</span>], input_dim=X_train.shape[<span style="color:#00D">1</span>], output_dim=<span style="color:#00D">10</span>, ) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">nn_example</span>(data): net1 = NeuralNet( layers=[(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">input</span><span style="color:#710">'</span></span>, layers.InputLayer), (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">hidden</span><span style="color:#710">'</span></span>, layers.DenseLayer), (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">output</span><span style="color:#710">'</span></span>, layers.DenseLayer), ], <span style="color:#777"># layer parameters:</span> input_shape=(<span style="color:#069">None</span>, <span style="color:#00D">28</span>*<span style="color:#00D">28</span>), hidden_num_units=<span style="color:#00D">100</span>, <span style="color:#777"># number of units in 'hidden' layer</span> output_nonlinearity=lasagne.nonlinearities.softmax, output_num_units=<span style="color:#00D">10</span>, <span style="color:#777"># 10 target values for the digits 0, 1, 2, ..., 9</span> <span style="color:#777"># optimization method:</span> update=nesterov_momentum, update_learning_rate=<span style="color:#60E">0.01</span>, update_momentum=<span style="color:#60E">0.9</span>, max_epochs=<span style="color:#00D">10</span>, verbose=<span style="color:#00D">1</span>, ) <span style="color:#777"># Train the network</span> net1.fit(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X_train</span><span style="color:#710">'</span></span>], data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y_train</span><span style="color:#710">'</span></span>]) <span style="color:#777"># Try the network on new data</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Feature vector (100-110): %s</span><span style="color:#710">&quot;</span></span> % data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X_test</span><span style="color:#710">'</span></span>][<span style="color:#00D">0</span>][<span style="color:#00D">100</span>:<span style="color:#00D">110</span>]) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Label: %s</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">str</span>(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y_test</span><span style="color:#710">'</span></span>][<span style="color:#00D">0</span>])) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Predicted: %s</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">str</span>(net1.predict([data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X_test</span><span style="color:#710">'</span></span>][<span style="color:#00D">0</span>]]))) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">main</span>(): data = load_data() print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Got %i testing datasets.</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">len</span>(data[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">X_train</span><span style="color:#710">'</span></span>])) nn_example(data) <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: main() </pre></div> </div> </div> <p>The output is</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># Neural Network with 79510 learnable parameters ## Layer information # name size --- ------ ------ 0 input 784 1 hidden 100 2 output 10 epoch train loss valid loss train/val valid acc dur ------- ------------ ------------ ----------- ----------- ----- 1 0.59132 0.32314 1.82993 0.90988 1.70s 2 0.30733 0.26644 1.15348 0.92623 1.96s 3 0.25879 0.23606 1.09629 0.93363 2.09s 4 0.22680 0.21424 1.05865 0.93897 2.13s 5 0.20187 0.19633 1.02827 0.94313 2.21s 6 0.18129 0.18187 0.99685 0.94758 1.81s 7 0.16398 0.16992 0.96506 0.95074 2.14s 8 0.14941 0.16020 0.93265 0.95262 1.88s 9 0.13704 0.15189 0.90222 0.95460 2.15s 10 0.12633 0.14464 0.87342 0.95707 2.21s Feature vector (100-110): [ 0. 0. 0. 0. 0. 0. 0. 0. 0. 0.] Label: 7 Predicted: [7] </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li><a href="http://www.pyimagesearch.com/2014/09/22/getting-started-deep-learning-python/">Getting Started with Deep Learning and Python</a></li> </ul> Echtzeitsysteme - Klausur //martin-thoma.com/echtzeitsysteme-klausur/ Tue, 14 Apr 2015 20:43:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/echtzeitsysteme-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Echtzeitsysteme&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://rob.ipr.kit.edu/mitarbeiter_96.php">Herrn Prof. Dr. Wörn</a> im Sommersemester 2015 gehört.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="vorlesung">Vorlesung</h3> <p>Der Dozent verwendete einige Abkürzungen, die mir nicht geläufig waren. Diese habe ich unter anderem in der folgenden Tabelle aufgeführt.</p> <table> <tr> <th>Datum</th> <th style="width:60px;">Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>14.04.2015</td> <td><a href="https://ilias.studium.kit.edu/ilias.php?ref_id=422667&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Kapitel 1</a> (ES1-1 - ES1-24)</td> <td><a href="https://de.wikipedia.org/wiki/Speicherprogrammierbare_Steuerung"><abbr title="Speicherprogrammierbare Steuerung">SPS</abbr></a>; NC; RC; <a href="https://de.wikipedia.org/wiki/Daisy_Chain">Daisy chain</a>; Mikroprozessor vs. Mikrorechner vs. Mikrorechnersystem; Aufbau eines Mikroprozessors; Speicherhierachie (L1-, L2- und L3-Cache, Hauptspeicher, Festplatte); superskalare Pipeline; Fixed- priority-preemptive Unterbrechungsbehandlung</td> </tr> <tr> <td>15.04.2015</td> <td><a href="https://ilias.studium.kit.edu/ilias.php?ref_id=422667&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Kapitel 1</a> (ES1-25 - ES1-60)</td> <td>Watchdogs, <a href="http://de.wikipedia.org/wiki/Jitter">Jitter</a>, <a href="http://de.wikipedia.org/wiki/Speicherdirektzugriff">DMA</a>, <a href="http://de.wikipedia.org/wiki/Digitaler_Signalprozessor">Signalprozessor</a>, <abbr title="Very long instruction word">VLIW</abbr>; verschiedene Bus-Arten (z.B. PCI-Bus), Bus-Arbitation kümmert sich bei mehreren Bus-Mastern um die Zugriffskontrolle. Das kann zentral oder dezentral (z.B. über eine Daisy-Chain oder einen Identifikationsbus) geschehen; </td> </tr> <tr> <td>21.04.2015</td> <td><a href="https://ilias.studium.kit.edu/ilias.php?ref_id=422667&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Kapitel 1</a> (ES1-62 - ES1-83)</td> <td>Arbitrierung; Transaktionen</td> </tr> <tr> <td>22.04.2015</td> <td><a href="https://ilias.studium.kit.edu/ilias.php?ref_id=423230&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Kapitel 2</a> (ES2-1 - ES2-?)</td> <td><a href="https://de.wikipedia.org/wiki/Ohmsches_Gesetz#Beschreibung">Ohmsches Gesetz</a>; Parallel- und Reihenschaltung von Widerständen; Spannungsteiler; <a href="https://de.wikipedia.org/wiki/Kirchhoffsche_Regeln#Der_Knotenpunktsatz_.28Knotenregel.29_.E2.80.93_1._Kirchhoffsches_Gesetz">Knotenregel</a>; <a href="https://de.wikipedia.org/wiki/Kirchhoffsche_Regeln#Der_Maschensatz_.28Maschenregel.29_.E2.80.93_2._Kirchhoffsches_Gesetz">Maschenregel</a>; Transistoren; Addierer; Differenzierer; Invertierter Addierer; Integrierer; AD/DA-Wandler</td> </tr> <tr> <td>28.04.2015</td> <td><a href="https://ilias.studium.kit.edu/ilias.php?ref_id=423230&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Kapitel 2</a> (?)</td> <td>?</td> </tr> <tr> <td>12.05.2015</td> <td>?</td> <td>Hurwitz-Kriterium; Ortskurve; P-, Pi- und PID-Regler (I: Rück-Knala, D: Änderung); Vorsteuerung, Car Cruise Control</td> </tr> <tr> <td>19.05.2015</td> <td>2. Übung</td> <td>Operationsverstärker, AD-Wandler</td> </tr> <tr> <td>20.05.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>26.05.2015</td> <td>3. Übung</td> <td>Mit Jessica Hutzl</td> </tr> <tr> <td>27.05.2015</td> <td>Kapitel 4 (- ES 4-43)</td> <td>ISO/OSI-Modell, Profibus, CAN-Bus, INTERBUS</td> </tr> <tr> <td>02.06.2015</td> <td>Kapitel 4, 5 (ES 4-44 - 5-16)</td> <td>Rechtzeitigkeit</td> </tr> <tr> <td>03.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>09.06.2015</td> <td>Übung</td> <td>Regelung</td> </tr> <tr> <td>10.06.2015</td> <td>Übung</td> <td>-</td> </tr> </table> <h3 id="abkrzungen">Abkürzungen</h3> <ul> <li>LLF: Least-Laxity-First-Scheduling</li> <li>EDF: Earliest-Deadline-First-Scheduling</li> <li>GPS: Guaranteed Percentage Scheduling</li> </ul> <h3 id="wichtiges">Wichtiges</h3> <ul> <li>Ist eine Übertragungsfunktion in Pol-und-Nullstellenform <code>$G(s)$</code> stabil? → Ja, falls der Realanteil aller Pole negativ ist.</li> <li>Ist eine Funktion <code>$G(s)$</code> stabile? → Ja, falls die Nullstellen der Gleichung <code>$G(s)+1=0$</code> links der <code>$i$</code>-Achse liegen.</li> <li>Ist <code>$G(i \omega)$</code> stabil? → Ja, falls die Kurve (-1, 0i) NICHT umfährt (siehe <a href="https://de.wikipedia.org/wiki/Stabilit%C3%A4tskriterium_von_Nyquist#Spezielles_Nyquistkriterium_.2F_.E2.80.9ELinke-Hand-Regel.E2.80.9C">Nyquistkriterium</a>)</li> </ul> <h4 id="hurwitz-kriterium">Hurwitz-Kriterium</h4> <p>Ein System <code>$a_n x^{(n)} + a_{n-1} x^{(n-1)} + \dots + a_1 \dot{x} + a_0 x = 0$</code> ist dann stabil, wenn</p> <ol> <li>alle Koeffizienten <code>$a_i &gt; 0$</code> UND</li> <li>alle <a href="https://de.wikipedia.org/wiki/Minor_(Lineare_Algebra)#Hauptminoren">Hauptabschnittsdeterminanten</a> (auch Hauptminoren genannt) positiv sind.</li> </ol> <p>Insbesondere gilt für <code>$a_2 \cdot \ddot{x} + a_1 \dot{x} + a_0 x = 0$</code>, dass die Hauptabschnittsdeterminanten von</p> <p><code> $$\begin{pmatrix}a_1 &amp; 0\\0 &amp; a_0\end{pmatrix}$$</code> zu überprüfen sind. Das ist jedoch schon durch das erste Kriterium erfüllt.</p> <p>Bei <code>$a_3 \cdot x^{(3)} + a_2 \cdot \ddot{x} + a_1 \dot{x} + a_0 x = 0$</code> ist</p> <p><code> $$\begin{pmatrix}a_2 &amp; a_0 &amp; 0\\1 &amp; a_1 &amp; 0\\ 0 &amp; a_2 &amp; 1\end{pmatrix}$$</code></p> <p>zu überprüfen, also:</p> <ul> <li><code>$a_2 &gt; 0$</code>?</li> <li><code>$a_2 \cdot a_1 - a_0 &gt; 0$</code>? (the determinant of size 2 and 3 is the same)</li> </ul> <h4 id="schaltungen">Schaltungen</h4> <ul> <li>Subtrahierer: <code>$U_A = \frac{R_0 (R_1 + R_3)}{R_1 (R_0 + R_2)} \cdot U_2 - \frac{R_3}{R_1} \cdot U_1$</code></li> <li>Invertierender Addierer: <code>$U_A = - \left (\sum_{i=1}^{N-1} \frac{U_i}{R_i} \right ) \cdot R_N$</code></li> <li>Integrierer: <code>$- \frac{1}{RC} \int U_E \mathrm{d}t$</code></li> <li>Differenzierer: <code>$U_A = - R_N \cdot I_E$</code></li> <li>Invertierender OP: <code>$y = - \frac{R_N}{R_1}$</code></li> <li>Nicht-Invertierender OP: <code>$y = \frac{R_N+R_1}{R_1}$</code></li> <li>Parallelverfahren (vgl. ES 2 - 37)</li> </ul> <h2 id="typische-klausur">Typische Klausur</h2> <p>Die Klausuren sind alle sehr ähnlich zu einander:</p> <ul> <li>Regelung <ul> <li>Zeitkonstante Regelung: 7 Punkte <ul> <li>Definition Regelung / Steuerung: 1 Punkt</li> <li>Laplace-Bereich / Übergangsfunktion: 1 Punkt</li> <li>Transformationstabelle / Differentialgleichung: 1 Punkt</li> <li>Ist ein gegebenes System stabil? (mit Übergangsfunktion): 1 Punkt</li> <li>PID-Regler / stabilität / Fehler: 2 Punkte</li> <li>Gütegrad von Regelungssystem: 1.5 Punkte</li> <li>Bode-Diagramm: 1.5 Punkte</li> </ul> </li> <li>Zeitdiskrete Regelung: 8 Punkte <ul> <li>Aliasing / Abtasttheorem: 1 Punkt</li> <li>Z-Transformierte Übertragungsfunktion G(z): 2 Punkte</li> <li>Z-Transformierte / PD-Regelalgorithmus: 1 Punkt</li> <li>Z-Transformierte / Regelkreis: 1 Punkt</li> <li>Differenzialgleichungen → Differenzengleichung: 2 Punkte</li> <li>Digital vs. Kontinuierlich (Diskretisierung): 1 Punkte</li> <li>Stabilität eines Systems: 1 Punkt</li> </ul> </li> </ul> </li> <li>Rechnerarchitekturen / Busse / Operationsverstärker <ul> <li>Rechnerarchitekturen und Busse: 10 Punkte <ul> <li>Watchdog: 1 Punkt</li> <li>Echtzeitausgabeeinheit (Konzept, Definition, Eigenschaften): 1 Punkt</li> <li>Befehlsskalarer Prozessor / Sprungbedingungen: 1 Punkt</li> <li>Bus-Eigenschaften: 2 Punkte <ul> <li>Echtzeitfähig oder nicht</li> <li>Synchron ↔ asynchron</li> <li>Getrennter Adress- und Datenbus ↔ multiplex</li> <li>Burst-Datentransfer erlaubt oder auch nicht</li> </ul> </li> </ul> </li> <li>Operationsverstärker in Analog- und Digitaltechnik: 8 Punkte <ul> <li>Schaltsymbol Operationsverstärker (mit Versorgungsspannung), Anschlüsse beschriften: 1 Punkt</li> <li>Eingangsströme (real/ideal): 1 Punkt</li> <li>Operationsverstärker: 4 Punkte</li> <li>Prinzip Operationswandler: 1 Punkt</li> <li>Asymmetrische / differenzielle Datenübertragung: 1 Punkt</li> <li>A/D-Wandler: 2 Punkte</li> </ul> </li> </ul> </li> <li>Echtzeitkommunikation / Programmierung: 7 Punkte <ul> <li>ISO / OSI-Schichtenmodell: 1.5 Punkte</li> <li>Manchester-Codierung: 1.5 Punkte</li> <li>Übertragungsfehler: 1.5 Punkte</li> <li>CAN-Dataframes: 2.5 Punkte</li> <li>Zusätzliche Forderungen an Echtzeitsysteme: 1 Punkt</li> <li>FPP-Scheduling: 2 Punkte</li> <li>Periodenabweichung: 2 Punkte</li> <li>Optimales Scheduling: 1 Punkt</li> <li>Schwankungen: 1 Punkt</li> </ul> </li> <li>Echtzeit-OS / SPS <ul> <li>Echtzeit-OS: 7 Punkte <ul> <li>Zusätzliche Anforderungen: 1 Punkt</li> <li>Zusätzliche Anforderungen Middleware: 1 Punkt</li> <li>Beispiele: 1 Punkt</li> <li>Sperrsynchronisation: 2 Punkte</li> <li>Seitenadressierung: 2 Punkte</li> </ul> </li> <li>SPS: 8 Punkte <ul> <li><abbr title="Funktionspointer">FUP</abbr> → <abbr title="Anweisungsliste">AWL</abbr>: 2.5 Punkte</li> <li>FUP → Structured Text: 2.5 Punkte</li> <li>3 Verarbeitungsschirtte von SPS im zyklischen Programmbetrieb: 1 Punkt</li> <li>Konventionelle SPS ↔ Soft: 1 Punkt</li> <li>Graphische ↔ textuelle Programmiersprache: 1 Punkt</li> </ul> </li> </ul> </li> </ul> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://www.math.kit.edu/stoch/lehre/wt2015s/de">Vorlesungswebsite</a></li> <li><a href="https://ilias.studium.kit.edu/goto_produktiv_crs_409322.html">Ilias</a></li> <li><a href="https://github.com/MartinThoma/KIT-Musterloesungen/tree/master/Echtzeitsysteme">Klausur-Musterlösungen</a></li> <li>Meine <a href="https://ankiweb.net/shared/info/1877369263">Anki-Karten</a> (bestehend aus Teilen von <a href="https://ankiweb.net/shared/info/2095784594">Echtzeitsysteme - KIT Wörn</a> und <a href="https://ankiweb.net/shared/info/2071108701">Echtzeitsysteme KIT Wörn Wissensfragen Klausur</a> sowie weiteren Karten)</li> </ul> <p>StackOverflow:</p> <ul> <li><a href="http://stackoverflow.com/q/3851677/562769">What is the difference between DMA and memory-mapped IO?</a></li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <ul> <li>Wo sind die Übungsblätter: ? (Ilias?)</li> <li>Abgabeform: Keine Abgabe</li> <li>Abgabe (wochentag): Keine Abgabe</li> <li>Rücknahme: -</li> <li>Turnus: ?</li> <li>Übungsschein verpflichtend: Es gibt keinen Übungsschein.</li> <li>Bonus durch Übungsschein: Es gibt keinen Übungsschein.</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Donnerstag, der 24.09.2015 von 14:00 Uhr-15:00 Uhr (<a href="http://www.informatik.kit.edu/klausuren.php?kid=522.35">Quelle</a>)<br /> <strong>Ort</strong>: Gehrtsen HS (<a href="https://www.kithub.de/map/2144">Geb. 30.21</a>)<br /> <strong>Punkte</strong>: 60<br /> <strong>Punkteverteilung</strong>: 4 Aufgaben à 15 Punkte:</p> <ul> <li>Regelung</li> <li>Rechnerarchitekturen, Busse, Operationsverstärker, Analog-/Digitaltechnik</li> <li>Echtzeitkommunikation und Echtzeitprogrammierung</li> <li>Echtzeitbetriebssysteme und SPS</li> </ul> <p><strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: Gibt es nicht.<br /> <strong>Bonuspunkte</strong>: Gibt es nicht.<br /> <strong>Ergebnisse</strong>: Die Noten der Klausur werden am Schwarzen Brett im IAR-IPR (Geb. 40.28, Foyer, links) ausgehängt. Noch ist nichts da (Stand: 24.09.2015)<br /> <strong>Einsicht</strong>: wird über <a href="https://ilias.studium.kit.edu/goto_produktiv_fold_450985.html">Ilias</a> bekannt gegeben<br /> <strong>Erlaubte Hilfsmittel</strong>: Keine</p> <h2 id="fazit">Fazit</h2> <p>Dieses Modul kann man sich getrost schenken. Wenn man vorher nichts von Regelungstechnik weiß, ist man hinterher auch nicht schlauer. Es scheint so zu sein, dass die klausurrelevanten Teile alle in den Übungen besprochen werden.</p> <p>Die bereitgestellten <strong>Materialien</strong> hätten besser sein können. Es gibt zwar ein Skript welches sogar eine ISBN-Nummer hat, aber insbesondere bei dem Regelungstechnik-Teil ist es nicht sonderlich hilfreich. Ich hatte das Gefühl, dass mir da einfach Grundlagen fehlen. Diese werden auch nicht erklärt. Zu den PDF-Folien muss man sagen, dass diese zwar schnell im Ilias hochgeladen wurden, aber teilweise zu viele Informationen hatten. Es war nicht klar, was wichtig ist. Außerdem hat teilweise, wenn man nur die Folien angesehen hat, der Kontext gefehlt.</p> <p>Ein <strong>Highlight</strong> waren Videos, in denen Roboter Kugeln auf einem Tablett sehr schnell transportieren. Dazu müssen die Roboter das Tablett im richtigen Winkel neigen. Das war ein Highlight der Vorlesung. Schade, dass nie erklärt wurde wie so etwas berechnet wird.</p> <p><strong>Vorwissen</strong> in der Regelungstechnik und bei Differentialgleichungen ist sicher hilfreich.</p> <p>Die <strong>Klausurvorbereitung</strong> besteht hauptsächlich aus Auswendiglernen. Verständnis ist wohl nicht nötig (mal schauen… ich konnte keinen Notenschlüssel finden.), da die Klausuren immer nahezu identisch aufgebaut sind.</p> <p>Meine <strong>Empfehlung</strong> an Studenten ist, in die Übung zu gehen. Da kommen die klausurrelevanten Sachen. Teilweise 1-zu-1 die gleichen Fragen.</p> <p><strong>Verbesserungsvorschläge</strong> für die Dozenten hätte ich auch ein paar:</p> <ol> <li>Es sollte Tutorien geben.</li> <li>Es sollte einen verpflichtenden Übungsschein geben. Mit 50% der Punkte hat man den Übungsschein, ab 75% gibts Bonuspunkte für die Klausur. Diese Übungsblätter werden von den Tutoren korrigiert und besprochen. Wenn die Studenten es reihenweise nicht schaffen merkt man schon, wo man die Vorlesung verbessern muss.</li> <li>Veröffentlichung der Musterlösungen zu den Klausuren.</li> <li>Anpassung des Skripts, z.B. wurde der VME-Bus durch den PCIe-Bus ersetzt.</li> <li>Anpassung des Modulhandbuchs. Man sollte den Leuten <em>empfehlen</em>, zuvor die Vorlesung “Betriebssysteme” gehört zu haben.</li> <li>Ein <a href="https://de.wikibooks.org/wiki/Hauptseite">Wikibook</a> beginnen. Wenn man das für jedes Modul machen würde, könnte man auch Abhängigkeiten besser sehen und Studenten könnten fehlendes Wissen leichter nachholen. Außerdem würde man das Wissen frei verfügbar machen und man könnte die Exzellenz der Lehre zeigen, falls man wirklich der Meinung ist die Lehre am KIT sei exzellent. Über die Diskussionsseiten könnten Studenten und andere weitgehend anonym ihre Fragen stellen und Verbesserungsvorschläge machen. Über das Wiki-System könnten freiwillige Helfer insbesondere bei zeitaufwendigen Grafiken helfen.</li> </ol> Markovsche Ketten - Klausur //martin-thoma.com/markovketten-klausur/ Mon, 13 Apr 2015 13:42:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/markovketten-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Markovsche Ketten&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn <a href="http://www.math.kit.edu/stoch/~klar/de">Dr. Bernhard Klar</a> im Sommersemester 2015 gehört. Der Artikel wird bis zur Klausur laufend erweitert.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <p>Es wäre toll, wenn ich von jeder Vorlesung einen Mitschrieb hochladen könnte. Gibt es Leute, die eine Kamera / einen Scanner haben und mir ihren Mitschrieb als JPG-Bilder schicken würden? Einfach an info@martin-thoma.de schicken.</p> <h3 id="vorlesung">Vorlesung</h3> <p>Zur Vorlesung gibt es das Skript “Markov-Ketten” von Frau Prof. Dr. Bäuerle. (Ich habe eine Version von 2012).</p> <table> <tr> <th>Datum</th> <th>Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>13.04.2015</td> <td>0. Beispiele (<a href="//martin-thoma.com/pdf/markovketten-2015-04-13.pdf">Mitschrieb</a>)</td> <td>Einführung in Markovketten mit vielen Beispielen (Weg des Betrunkenen, Ehrenfest-Modell, Irrfahrt, Vererbung); absorbierende Zustände; stochastische Matrix</td> </tr> <tr> <td>16.04.2015</td> <td>1. </td> <td>Konstruktion von Markov-Ketten</td> </tr> <tr> <td>20.04.2015</td> <td></td> <td></td> </tr> <tr> <td>21.04.2015</td> <td>3.10 - 4.6 (<a href="//martin-thoma.com/pdf/markovketten-2015-05-21.pdf">Mitschrieb</a>)</td> <td>Total-Variationsabstand, `$d(\mu, \nu) = \frac{1}{2} \sum_{i \in S} |\mu(i)- \nu(i)|$`, Periode, aperiodisch, ein Konvergenzsatz, Kopplungsargument</td> </tr> </table> <h2 id="material-und-links">Material und Links</h2> <h3 id="kit">KIT</h3> <ul> <li><a href="http://www.math.kit.edu/stoch/lehre/mk2015s/de">Vorlesungswebsite</a></li> <li><a href="https://ilias.studium.kit.edu/goto_produktiv_crs_411041.html">Ilias</a></li> </ul> <h3 id="sonstiges">Sonstiges</h3> <ul> <li><a href="http://setosa.io/blog/2014/07/26/markov-chains/">Markov Chains</a>: A very short introduction to markov chains with beautiful visualizations</li> </ul> <h3 id="wichtigster-stoff">Wichtigster Stoff</h3> <p>Wie immer Definitionen (Markovkette, transient, rekurrent, Klasse, irreduzibel)</p> <p>Wenn man die Matrix so umsortiert, dass rechts unten die rekurrenten Zustände sind (das ist nicht immer eine Einheitsmatrix!), Dann heißt die Matrix links oben <code>$Q$</code> und rechts oben <code>$R$</code>. Dann gilt:</p> <ul> <li><code>$(E-Q)^{-1} \cdot R$</code>: Absorptionszeit</li> <li><code>$(E-Q)^{-1} \cdot \begin{pmatrix}1\\\vdots\\1\end{pmatrix}$</code>: Schritte bis zur Absorption.</li> <li>Invariantes Maß finden: <code>$\pi P = \pi$</code> bzw. <code>$\pi Q = 0$</code> im zeitkontinuierlichen Fall</li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <p>Es gibt Dienstags und Mittwochs Tutorien.</p> <ul> <li>Wo sind die Übungsblätter: <a href="https://ilias.studium.kit.edu/goto_produktiv_fold_411044.html">Ilias</a></li> <li>Abgabeform: Handgeschrieben (?)</li> <li>Abgabe: ?</li> <li>Rücknahme: ?</li> <li>Turnus: Wöchentlich</li> <li>Übungsschein verpflichtend: Nein</li> <li>Bonus durch Übungsschein: Nein</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Montag, der 03.08.2015 von 11:00 bis 13:00 Uhr (<a href="http://www.math.kit.edu/stoch/lehre/mk2015s/event/mk-klausur/">Quelle</a>)<br /> <strong>Ort</strong>: <a href="http://www.kithub.de/map/2086">Daimler-Hörsaal</a> (Geb. 10.11, <a href="http://www.math.kit.edu/stoch/lehre/mk2015s/event/mk-klausur/">Quelle</a>)<br /> <strong>Punkte</strong>: 60<br /> <strong>Punkteverteilung</strong>: 6 Aufgaben mit 9-13 Punkten<br /> <strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: ?<br /> <strong>Bonuspunkte</strong>: ?<br /> <strong>Ergebnisse</strong>: ?<br /> <strong>Einsicht</strong>: Montag, 19.10.2015, 13:00 Uhr - 13:30 Uhr, Im Raum 2.071, <a href="https://www.kithub.de/map/2133">Mathematikgebäude</a><br /> <strong>Erlaubte Hilfsmittel</strong>: ?</p> Wahrscheinlichkeitstheorie-Klausur //martin-thoma.com/wahrscheinlichkeitstheorie-klausur/ Mon, 13 Apr 2015 10:37:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wahrscheinlichkeitstheorie-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Wahrscheinlichkeitstheorie&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn Prof. Dr. Henze im Sommersemester 2015 gehört. Der Artikel wird bis zur Klausur laufend erweitert.</div> <p>Der Dozent veweist immer wieder auf die Vorlesung Analysis III und insbesondere das Skript von Prof. Hundertmark. Kann mir das jemand schicken?</p> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="vorlesung">Vorlesung</h3> <table> <tr> <th>Datum</th> <th>Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>13.04.2015</td> <td>Maßtheoretische Grundlagen <a href="https://ilias.studium.kit.edu/ilias.php?ref_id=422503&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">0.1 - 1.13</a></td> <td>Wiederholung von Begriffen: <a href="https://de.wikipedia.org/wiki/Ma%C3%9F_(Mathematik)#Definition">Maß</a>, <a href="https://de.wikipedia.org/wiki/%CE%A3-Algebra#Definition">`$\sigma$`-Algebra</a>, <a href="https://de.wikipedia.org/wiki/Halbring_(Mengensystem)#Definition">Halbring</a>, <a href="https://de.wikipedia.org/wiki/Dynkin-System#Definition">Dynkin-System</a>, Durchschnittsstabilität (`$A, B \in \mathcal H \Rightarrow A \cap B \in \mathcal H$`)</td> </tr> <tr> <td>15.04.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>20.04.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>27.04.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>29.04.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>04.05.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>11.05.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>13.05.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>18.05.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>27.05.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>01.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>03.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>10.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>15.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>22.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>24.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>29.06.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>06.07.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>08.07.2015</td> <td>?</td> <td>?</td> </tr> <tr> <td>13.07.2015</td> <td>?</td> <td>?</td> </tr> </table> <h2 id="material-und-links">Material und Links</h2> <ul> <li><a href="http://www.math.kit.edu/stoch/lehre/wt2015s/de">Vorlesungswebsite</a></li> <li><a href="https://ilias.studium.kit.edu/ilias.php?ref_id=419886&amp;cmd=frameset&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Ilias</a></li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <ul> <li>Wo sind die Übungsblätter: ?</li> <li>Abgabeform: ?</li> <li>Abgabe: ?</li> <li>Rücknahme: ?</li> <li>Turnus: ?</li> <li>Übungsschein verpflichtend: ?</li> <li>Bonus durch Übungsschein: ?</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Donnerstag, der 30.07.2015 von 11:00 bis 13:00 Uhr (<a href="https://ilias.studium.kit.edu/ilias.php?ref_id=422581&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Quelle</a>)<br /> <strong>Ort</strong>: <a href="http://www.kithub.de/map/2289">Hertz-Hörsaal</a> (Geb. 10.11, <a href="https://ilias.studium.kit.edu/ilias.php?ref_id=422581&amp;cmd=sendfile&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Quelle</a>)<br /> <strong>Punkte</strong>: ?<br /> <strong>Punkteverteilung</strong>: ?<br /> <strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: ?<br /> <strong>Bonuspunkte</strong>: ?<br /> <strong>Ergebnisse</strong>: ?<br /> <strong>Einsicht</strong>: ?<br /> <strong>Erlaubte Hilfsmittel</strong>: ?</p> Python Code Documentation //martin-thoma.com/python-code-documentation/ Wed, 08 Apr 2015 19:39:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-code-documentation <p>Documentating your code is important when you make non-trivial projects. The standard way to document Python code is with <a href="http://sphinx-doc.org/">Sphinx</a>. You write the documentation files with <a href="http://docutils.sourceforge.net/docs/ref/rst/restructuredtext.html">reStructuredText</a>.</p> <p>One of the most important Sphinx plugins is <a href="http://sphinx-doc.org/ext/autodoc.html">autodoc</a>. This allows you to generate the documentation of modules, classes and functions automatically by using their docstrings.</p> <p>There are 3 standard ways to write docstrings: Sphinxy, Googley or NumPyDocy.</p> <h2 id="the-sphinx-way">The Sphinx Way</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">preprocessing</span>(<span style="color:#069">self</span>, algorithms): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Apply preprocessing algorithms.</span><span> </span><span> </span><span> :param algorithms: Preprocessing allgorithms which get applied in order.</span><span> </span><span> :type algorithms: a list objects</span><span> </span><span> </span><span> &gt;&gt;&gt; import preprocessing</span><span> </span><span> &gt;&gt;&gt; a = HandwrittenData(...)</span><span> </span><span> &gt;&gt;&gt; preprocessing_queue = [(preprocessing.scale_and_shift, []),</span><span> </span><span> ... (preprocessing.connect_strokes, []),</span><span> </span><span> ... (preprocessing.douglas_peucker,</span><span> </span><span> ... {'EPSILON': 0.2}),</span><span> </span><span> ... (preprocessing.space_evenly,</span><span> </span><span> ... {'number': 100,</span><span> </span><span> ... 'KIND': 'cubic'})]</span><span> </span><span> &gt;&gt;&gt; a.preprocessing(preprocessing_queue)</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">type</span>(algorithms) <span style="color:#080;font-weight:bold">is</span> <span style="color:#369;font-weight:bold">list</span> <span style="color:#080;font-weight:bold">for</span> algorithm <span style="color:#080;font-weight:bold">in</span> algorithms: algorithm(<span style="color:#069">self</span>) </pre></div> </div> </div> <h2 id="the-google-way">The Google Way</h2> <p>Google documented its format at <a href="http://google-styleguide.googlecode.com/svn/trunk/pyguide.html">http://google-styleguide.googlecode.com/</a>. (I’m wondering where that will move, now that they plan to shut code.google.com down. Probably to GitHub.)</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">preprocessing</span>(<span style="color:#069">self</span>, algorithms): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Apply preprocessing algorithms.</span><span> </span><span> </span><span> Args:</span><span> </span><span> algorithms (a list objects): Preprocessing allgorithms which get</span><span> </span><span> applied in order.</span><span> </span><span> </span><span> Examples:</span><span> </span><span> </span><span> &gt;&gt;&gt; import preprocessing</span><span> </span><span> &gt;&gt;&gt; a = HandwrittenData(...)</span><span> </span><span> &gt;&gt;&gt; preprocessing_queue = [(preprocessing.scale_and_shift, []),</span><span> </span><span> ... (preprocessing.connect_strokes, []),</span><span> </span><span> ... (preprocessing.douglas_peucker,</span><span> </span><span> ... {'EPSILON': 0.2}),</span><span> </span><span> ... (preprocessing.space_evenly,</span><span> </span><span> ... {'number': 100,</span><span> </span><span> ... 'KIND': 'cubic'})]</span><span> </span><span> &gt;&gt;&gt; a.preprocessing(preprocessing_queue)</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">type</span>(algorithms) <span style="color:#080;font-weight:bold">is</span> <span style="color:#369;font-weight:bold">list</span> <span style="color:#080;font-weight:bold">for</span> algorithm <span style="color:#080;font-weight:bold">in</span> algorithms: algorithm(<span style="color:#069">self</span>) </pre></div> </div> </div> <p>To get the google way render well in Sphinx, you need <a href="https://pypi.python.org/pypi/sphinxcontrib-napoleon">Napoleon</a>.</p> <h2 id="the-numpydoc-way">The NumPyDoc Way</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">preprocessing</span>(<span style="color:#069">self</span>, algorithms): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Apply preprocessing algorithms.</span><span> </span><span> </span><span> Parameters</span><span> </span><span> ----------</span><span> </span><span> algorithms : a list objects</span><span> </span><span> Preprocessing allgorithms which get applied in order.</span><span> </span><span> </span><span> Examples</span><span> </span><span> --------</span><span> </span><span> &gt;&gt;&gt; import preprocessing</span><span> </span><span> &gt;&gt;&gt; a = HandwrittenData(...)</span><span> </span><span> &gt;&gt;&gt; preprocessing_queue = [(preprocessing.scale_and_shift, []),</span><span> </span><span> ... (preprocessing.connect_strokes, []),</span><span> </span><span> ... (preprocessing.douglas_peucker,</span><span> </span><span> ... {'EPSILON': 0.2}),</span><span> </span><span> ... (preprocessing.space_evenly,</span><span> </span><span> ... {'number': 100,</span><span> </span><span> ... 'KIND': 'cubic'})]</span><span> </span><span> &gt;&gt;&gt; a.preprocessing(preprocessing_queue)</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">type</span>(algorithms) <span style="color:#080;font-weight:bold">is</span> <span style="color:#369;font-weight:bold">list</span> <span style="color:#080;font-weight:bold">for</span> algorithm <span style="color:#080;font-weight:bold">in</span> algorithms: algorithm(<span style="color:#069">self</span>) </pre></div> </div> </div> <p>To make numpydoc render well, you need the <a href="https://pypi.python.org/pypi/numpydoc">numpydoc sphinx extension</a>.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="https://github.com/numpy/numpy/blob/master/doc/HOWTO_DOCUMENT.rst.txt">A Guide to NumPy/SciPy Documentation</a></li> <li><a href="http://sphinxcontrib-napoleon.readthedocs.org/en/latest/example_numpy.html">sphinxcontrib-napoleon.readthedocs.org</a>: A longer numpydoc example</li> </ul> Python ctypes //martin-thoma.com/python-ctypes/ Thu, 02 Apr 2015 22:06:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-ctypes <p>One pseudo-problem people often mention when talking about Python is that Python is (too) slow. What they seem to forget or don’t know is that you can call C code from Python with <a href="https://docs.python.org/3/library/ctypes.html"><code>ctypes</code></a>. So you can get almost as fast as you can get with C; you’re not limited by the language in that respect. And most of the time your code has other issues when it is too slow.</p> <p>Now, you can also wrap Rust code with ctypes for Python ☺</p> <h2 id="motivation">Motivation</h2> <p>As a very simple example, I prepared a dumb Fibonacci implementation written in Python:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">fib</span>(n): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Calculate the n-th Fibonacci number.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">if</span> n &lt;= <span style="color:#00D">1</span>: <span style="color:#080;font-weight:bold">return</span> n <span style="color:#080;font-weight:bold">else</span>: <span style="color:#080;font-weight:bold">return</span> fib(n-<span style="color:#00D">1</span>) + fib(n-<span style="color:#00D">2</span>) <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: n = <span style="color:#00D">37</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">The %ith Fibonacci number is %i.</span><span style="color:#710">&quot;</span></span> % (n, fib(n))) </pre></div> </div> </div> <p>and exactly the same for Rust</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pub extern fn fib(n: u32) -&gt; u32 { if n &lt;= 1 { return n; } else { return fib(n-1) + fib(n-2); } } fn main() { let n = 37; println!(&quot;The {0}th Fibonacci number is {1}.&quot;, n, fib(n)) } </pre></div> </div> </div> <p>The execution times are quite different. Rust needs 0.40 seconds while Python 3 needs 15.7 seconds. That is almost 40× the time of Rust!</p> <p>Wouldn’t it be great if we could call the Rust function from Python?</p> <h2 id="example">Example</h2> <p>I’ll explain in the next chapters what is done, but at first you should see that there are only minor changes / overhead:</p> <p><strong>fibonacci.rt</strong>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>#![crate_type = &quot;dylib&quot;] #[no_mangle] pub extern fn fib(n: u32) -&gt; u32 { if n &lt;= 1 { return n; } else { return fib(n-1) + fib(n-2); } } </pre></div> </div> </div> <p>Call <code>rustc -O fibonacci.rt</code> to generate the library.</p> <p>Python:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>#!/usr/bin/env python import ctypes fiblib = ctypes.CDLL(&quot;./libfibonacci.so&quot;) fib = fiblib.fib n = 37 print(&quot;The %ith Fibonacci number is %i.&quot; % (n, fib(n))) </pre></div> </div> </div> <p>Now, taking the Python code, it takes only 0.44 seconds!</p> <h2 id="what-happens">What happens</h2> <p>The line <code>#![crate_type = "dylib"]</code> tells <code>rustc</code> that it has to create a dynamic library.</p> <p>The line <code>#[no_mangle]</code> tells the compiler not to mangle the name <code>fib</code>. This is important so that we can later use it from Python. (I think names are mangled to prevent name clashes … so it’s a kind of name-spacing.)</p> <p>Then we load the C DLL with <code>ctypes.CDLL("./libfibonacci.so")</code> and use it as expected. Pretty easy, isn’t it?</p> <h2 id="caveats">Caveats</h2> <p>Python makes some things very simple which are not that simple at all. Think about numbers, for example. In Rust, you have integers with 64 bits. But in Python you have arbitrary length integers. This might lead to problems.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="http://harkablog.com/calling-rust-from-c-and-python.html">Calling Rust from C (and Python!)</a></li> <li><a href="http://doc.rust-lang.org/book/">doc.rust-lang.org/book/ffi</a>: Foreign Function Interface</li> <li><a href="http://doc.rust-lang.org/reference.html#ffi-attributes">doc.rust-lang.org</a>: FFI attributes</li> <li><a href="http://rustbyexample.com/attribute/crate.html">rustbyexample.com</a>: Crates</li> </ul> The Rust Programming Language //martin-thoma.com/rust/ Thu, 26 Mar 2015 16:25:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/rust <p><a href="https://en.wikipedia.org/wiki/Rust_(programming_language)">Rust</a> is a compiled programming language which aims to replace C++. The designers wanted it to be similar fast, give the programmer similar fine-grained control over memory management, but more safety.</p> <p>Rust does so by introducing the concept of <a href="https://doc.rust-lang.org/book/ownership.html"><em>ownership</em></a>, <a href="https://doc.rust-lang.org/book/references-and-borrowing.html"><em>borrowing</em></a> and <a href="https://doc.rust-lang.org/book/lifetimes.html"><em>lifetimes</em></a> of variables. Rust also makes sure that after the scope is finished, the memory of variables gets de-allocated.</p> <p>I think <abbr title="Foreign Function Interface">FFI</abbr> is interesting. It allows Rust to “talk” with C code.</p> <p>Rust 1.0 was just released (<a href="http://blog.rust-lang.org/2015/05/15/Rust-1.0.html">source</a>). This means the language should be stable.</p> <p>If you want to know more, you should take a look at the beautiful <a href="https://doc.rust-lang.org/intro.html">A 30-minute Introduction to Rust</a>.</p> <h2 id="syntax-example">Syntax Example</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>fn fib(n: u32) -&gt; u32 { if n &lt;= 1 { return n; } else { return fib(n-1) + fib(n-2); } } fn main() { let n = 36; println!(&quot;The {0}th Fibonacci number is {1}.&quot;, n, fib(n)) } </pre></div> </div> </div> <h2 id="video-introduction">Video introduction</h2> <iframe width="512" height="288" src="https://www.youtube-nocookie.com/embed/agzf6ftEsLU?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="comparison">Comparison</h2> <ul> <li><a href="http://benchmarksgame.alioth.debian.org/u32/compare.php?lang=rust&amp;lang2=gpp">benchmarksgame</a> shows that rust is similar fast as C++. For some games it is faster, for some slower. Sometimes it needs less code, sometimes more.</li> <li><a href="http://stackoverflow.com/questions/tagged/rust?sort=votes&amp;pageSize=50">stackoverflow</a> has only 1781 questions of which are 102 unanswered (5.7%). C++ has 356,824 questions and 55,172 questions are not answered (15.5%). But I guess that will change as soon as more people use Rust (and libraries written in Rust).</li> <li><a href="http://githut.info/#Rust">GitHub</a>: Wow, Rust seems to be growing fast!</li> </ul> <h2 id="tools">Tools</h2> <p>As rust is still in very heavy development, you should build it yourself from the <a href="https://github.com/rust-lang/rust">source at GitHub</a>. Don’t worry, there are very detailed instructions. (But it takes <em>a lot</em> of time to compile.)</p> <ul> <li><a href="https://github.com/rust-lang/cargo"><code>cargo</code></a> package manager</li> <li>Syntax Highlighting and auto completion for ST3 (<a href="https://packagecontrol.io/packages/Rust">via Package Control</a>) <ul> <li>Auto completion with <a href="https://github.com/phildawes/racer">Racer</a></li> </ul> </li> </ul> <h2 id="comparison-to-c">Comparison to C++</h2> <blockquote> <p>1: No crashes because of code misuse (as long as you do not use unsafe {} )</p> <p>2: No memory leaks</p> <p>3: No data races (so you can thread this thing like mad, but better is has async task handling (crs pattern to). So lighting up your machines cores is no prob.</p> <p>4: Cross platform (really much better than most)</p> <p>5: Inbuilt version management, build system and test harness (with benchmarking to).</p> <p>6: Package management system (no more I Cannot build XX, it becomes automatic)</p> <p>7: Inbuilt generics and traits (c++ concepts and more)</p> <p>8: Very strongly typed (near zero runtime)</p> <p>9: Very fast</p> <p>10 compiles into a c lib basically (easy integration)</p> </blockquote> <p>Source: <a href="https://forum.safenetwork.io/t/rust-vs-c/3216">dirvine</a></p> <h2 id="see-also">See also</h2> <ul> <li><a href="http://www.rust-lang.org/">www.rust-lang.org</a>: Official Website</li> <li><a href="https://doc.rust-lang.org/std/fmt/">doc.rust-lang.org</a>: Shown with <code>fmt</code> - looks very nice! <ul> <li><a href="https://doc.rust-lang.org/intro.html">doc.rust-lang.org/intro.html</a></li> <li><a href="https://doc.rust-lang.org/book/">doc.rust-lang.org/book/</a></li> <li><a href="https://doc.rust-lang.org/reference.html">doc.rust-lang.org/reference.html</a></li> </ul> </li> <li><a href="http://blog.rust-lang.org/2015/02/13/Final-1.0-timeline.html">blog.rust-lang.org</a></li> <li><a href="https://crates.io/">crates.io</a>: Hosting site for community packages ☺</li> <li><a href="http://rustbyexample.com/">rustbyexample.com</a> <ul> <li><a href="http://www.joshondesign.com/2014/09/17/rustlang">joshondesign.com/2014/09/17/rustlang</a>: A short introduction to Rust with a tiny ray tracer.</li> </ul> </li> <li><a href="http://learnxinyminutes.com/docs/rust/">learnxinyminutes.com/docs/rust</a></li> </ul> <h2 id="conclusion">Conclusion</h2> <p>Rust looks very, very interesting. I am usually not a fan of new languages (e.g. I don’t see a reason to use <a href="https://en.wikipedia.org/wiki/Go_(programming_language)">Go</a>, <a href="https://en.wikipedia.org/wiki/Swift_(programming_language)">Swift</a> … not to speak of <a href="https://en.wikipedia.org/wiki/Clojure">Clojure</a>, <a href="https://en.wikipedia.org/wiki/Julia_(programming_language)">Julia</a>, <a href="https://en.wikipedia.org/wiki/TypeScript">TypeScript</a>, <a href="https://en.wikipedia.org/wiki/Dart_(programming_language)">Dart</a>). Most of the time, I don’t see anything new which is better than in existing languages and almost always the material around (tools, libraries, community) is much worse than in existing solutions.</p> <p>This seems to be different with Rust. Rust seems to provide everything I enjoy from Python, but in the fast, explicitly typed world.</p> <p>@<a href="http://schickling.me/">Johannes</a>: Thanks for pointing me to Rust ☺</p> Dreamspark SDM Odysee //martin-thoma.com/dreamspark-sdm-odysee/ Tue, 24 Mar 2015 13:04:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/dreamspark-sdm-odysee <p>I need to have Windows for work. As a student I <em>should</em> have free access to it. But when I try to download it, I have to use Microsofts “Secure Download Manager” (SDM). As a Ubuntu (Linux) user, this is easier said than done.</p> <h2 id="tldr">TL;DR</h2> <p>You need a Windows PC to download Windows. Ask a friend to download it. That might be the easiest way. If you have a Windows PC and get the same error as I get, you might need to re-install the system. (No, rebooting does not help.)</p> <p>What I’ve tried and what does not work:</p> <ul> <li>Wine</li> <li>VMs</li> <li>Avoiding SDM</li> </ul> <p>What I am currently trying: Installing Windows 7 on another computer.<em>argh</em></p> <p><strong>UPDATE: <a href="http://v3l0c1r4pt0r.tk/2014/06/01/how-to-download-from-dreamspark-bypassing-secure-download-manager/">How to bypass Secure Download Manager while downloading from Dreamspark</a> looks very promising.</strong></p> <h2 id="the-problem">The problem</h2> <p>Using the Windows 8 systems at my university gives:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/03/windows-sdm-screenshot.png"><img src="//martin-thoma.com/captions/windows-sdm-screenshot.png" alt="Error message when trying to install SDM" width="500" height="229" class="" /></a><p class="wp-caption-text">Error message when trying to install SDM</p></div> <blockquote> <p>Das Feature, das Sie verwenden möchten, befindet sich auf einer Netzressource, die nicht zur Verfügung steht.</p> <p>Klicken Sie auf “OK”, um den Vorgang zu wiederholen. Oder geben Sie in das untenstehende Feld den Pfad zu einem anderen Ordner ein, der das Installationspaket “SDM_DE.msi” enthält.</p> </blockquote> <p>(Sorry, I only get the German error message.)</p> <p>When I give the path of the SDM_DE.msi I get:</p> <blockquote> <p>Die Datei “Z:\sdm\SDM_DE.msi” ist kein gültiges Installationspaket für das Produkt “Secure Download Manager”. Suchen Sie das Installationspaket “SDM_DE.msi” in einem Order, von dem aus Sie “Secure Download Manager” installieren können.</p> </blockquote> <p>Then I got desperate and followed <a href="https://threadsofscience.wordpress.com/2013/02/13/downloading-dreamspark-microsoft-windows-on-ubuntu/">threadsofscience.wordpress.com/2013/02/13/downloading-dreamspark-microsoft-windows-on-ubuntu</a> (similar: http://boris-spinner.de/secure-download-manager-sdm-unter-linux-ausfuehren/).</p> <p>It seems as if I need Linux to emulate Windows to get Windows … it’s a strange world.</p> <blockquote> <p>wine: Bad EXE format for Z:\home\moose\Downloads\SDM_EN.msi.</p> </blockquote> <p>Seems to be a 32-bit / 64-bit problem …</p> <ul> <li>http://wiki.winehq.org/FAQ#32_bit_wineprefix</li> <li>https://appdb.winehq.org/objectManager.php?sClass=version&amp;iId=31542</li> </ul> <p>After trying to fix it, I get</p> <blockquote> <p>err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range fixme:storage:create_storagefile Storage share mode not implemented. err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range err:msidb:get_tablecolumns column 3 out of range err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range err:msidb:get_tablecolumns column 3 out of range err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range err:msidb:get_tablecolumns column 3 out of range err:msidb:get_tablecolumns column 1 out of range err:msidb:get_tablecolumns column 2 out of range err:msidb:get_tablecolumns column 3 out of range</p> </blockquote> <h2 id="reverse-engineering--a-little-bit">Reverse Engineering … a little bit</h2> <p>Taking a look at the <code>1234567890ab.sdx</code> file reveals that it contains only a single url:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>http://kit.onthehub.com/WebStore/Account/SdmAuthorize.aspx?o=12345678-1234-1234-123a-12234567890a&amp;ws=12345678-1234-1234-1234-1234567890ab&amp;uid=12345678-1234-1234-1234-1234567890ab&amp;abc=5 </pre></div> </div> </div> <p>(I’ve replaced the numbers by 123… to avoid problems with other people using my link to download stuff)</p> <p>However, I cannot simply download it there. There is a page with two downloads, but when I click on download nothing happens.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/03/sdm-download-page.png"><img src="//martin-thoma.com/captions/sdm-download-page.png" alt="SDM download page" width="500" height="340" class="" /></a><p class="wp-caption-text">SDM download page</p></div> <p>So I use Chrome developer tools (<kbd>Ctrl</kbd>+<kbd>shift</kbd>+<kbd>i</kbd>) to see the request.</p> <p>It’s a GET request which gets the response:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;information&gt;</span> <span style="color:#070;font-weight:bold">&lt;oiopua&gt;</span>12345678-1234-1234-1234-1234567890ab<span style="color:#070;font-weight:bold">&lt;/oiopua&gt;</span> <span style="color:#070;font-weight:bold">&lt;edv&gt;</span>1234567890^^1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789<span style="color:#070;font-weight:bold">&lt;/edv&gt;</span> <span style="color:#070;font-weight:bold">&lt;linkAvailable&gt;</span>1<span style="color:#070;font-weight:bold">&lt;/linkAvailable&gt;</span> <span style="color:#070;font-weight:bold">&lt;errorTextKey</span> <span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;invokeExternalDownload&gt;</span>0<span style="color:#070;font-weight:bold">&lt;/invokeExternalDownload&gt;</span> <span style="color:#070;font-weight:bold">&lt;fileURL&gt;</span>http://software.dreamspark.com/dreamspark/GERMAN/de_windows_8.1_with_update_x64_dvd_4048209.01.sdc<span style="color:#070;font-weight:bold">&lt;/fileURL&gt;</span> <span style="color:#070;font-weight:bold">&lt;/information&gt;</span> </pre></div> </div> </div> <p>Although I can download the <code>.sdc</code> file, I cannot use it. It is an encrypted file (which would give the <code>.iso</code>, but I don’t know how to encrypt it.).</p> <p>If you are interested in the file format, you might want to read <a href="https://en.wikipedia.org/wiki/Secure_Digital_Container">Secure Digital Container</a></p> <h2 id="vms">VMs</h2> <p>Another try is installing a VM. You can download some at https://www.modern.ie/en-us/virtualization-tools#downloads</p> <p>I downloaded IE11, Win 8.1. Importing the VM took about 15 minutes on my computer. Then I got another error:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/03/vm-critical-error.png"><img src="//martin-thoma.com/captions/vm-critical-error.png" alt="VM import error" width="500" height="359" class="" /></a><p class="wp-caption-text">VM import error</p></div> <h2 id="installing-windows-7">Installing Windows 7</h2> <p>12:50 I fortunately had a Windows 7 DVD lying around. Installing it will probably take another 2 hours or so…</p> <p>13:23 - <em>argh</em> … I just found another reason to hate Windows. I’ve just installed Windows 7. Cable-based network does not work out of the box. I have to install drivers from http://www.helpjet.net/files-Acer-TravelMate-5735Z.html#ANetwork</p> <h2 id="related">Related</h2> <ul> <li><a href="http://superuser.com/questions/734924/install-windows-8-1-from-dreamspark-download-on-ubuntu">Install Windows 8.1 from Dreamspark download on Ubuntu</a></li> <li><a href="//martin-thoma.com/why-are-microsoft-products-so-user-unfriendly/">Why are Microsoft products so User unfriendly?</a></li> </ul> HTTPie //martin-thoma.com/httpie/ Sun, 22 Mar 2015 17:50:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/httpie <p><a href="http://schickling.me/">Johannes</a> recently showed me <a href="https://github.com/jakubroztocil/httpie"><code>httpie</code></a>. It’s a very nice tool for sending HTTP requests. It is much simpler to use than <code>curl</code>.</p> <h2 id="installation">Installation</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo -H pip install httpie </pre></div> </div> </div> <h2 id="usage">Usage</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ http --form POST localhost:5000/api/recording recording=[{}] id=1 HTTP/1.0 200 OK Content-Length: 21 Content-Type: text/html; charset=utf-8 Date: Sun, 22 Mar 2015 15:50:27 GMT Server: Werkzeug/0.10.1 Python/2.7.8 edit recording with 1 </pre></div> </div> </div> <p>The output is colored in a very nice way:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/03/httpie-request.png"><img src="//martin-thoma.com/captions/httpie-request.png" alt="HTTPie in action" width="500" height="96" class="" /></a><p class="wp-caption-text">HTTPie in action</p></div> <h2 id="see-also">See also</h2> <ul> <li><a href="https://github.com/jakubroztocil/httpie">github.com/jakubroztocil/httpie</a></li> <li><a href="http://requestb.in/">requestb.in</a></li> </ul> Python and Encodings //martin-thoma.com/python-and-encodings/ Sat, 14 Feb 2015 14:28:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-and-encodings <p>Working with encodings different from ASCII or UTF-8 has always been work which I don’t like. It doesn’t feel very constructive to just make Python read a file / print some output.</p> <p>In the following, I will describe some strategies which might help you.</p> <h2 id="test-script">Test script</h2> <p>Copy the following text to a text file <code>test.txt</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Die süße, kleine, lärmende Überfliegerin lebt in der Haute-Côte-Nord. Dort hat es momemtan 32°C. </pre></div> </div> </div> <p>On Debian based systems you will get the information which type of encoding it has like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ file test.txt test.txt: UTF-8 Unicode text </pre></div> </div> </div> <p>This is probably the best result. But to make sure that we know how to deal with other encodings, you can change the encoding like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ iconv -f UTF-8 -t ISO-8859-1 test.txt &gt; test-iso-8859-1.txt $ file test-iso-8859-1.txt test-iso-8859-1.txt: ISO-8859 text </pre></div> </div> </div> <h2 id="source-code-encoding">Source code encoding</h2> <p>A first important step is to define the source code encoding. This is done with a comment. The first lines of Python code should probably always look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: UTF-8 -*-</span> </pre></div> </div> </div> <p><a href="https://www.python.org/dev/peps/pep-0263/">PEP-0263</a> explains it.</p> <h2 id="printing-encoding-problems">Printing encoding problems</h2> <p>The following error occurs when you try to print non-UTF-8 stuff with Python via Sublime Text:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[Decode error - output not utf-8] </pre></div> </div> </div> <p>The same code, executed via ZSH, gives:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Die s��e, kleine, l�rmende �berfliegerin lebt in der Haute-C�te-Nord. Dort hat es momemtan 32�C. </pre></div> </div> </div> <p>You can fix that by adjusting the code the following way:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: UTF-8 -*-</span> <span style="color:#777"># Make it work with Python 2 and Python 3</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">sys</span> PY3 = sys.version &gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">3</span><span style="color:#710">'</span></span> <span style="color:#080;font-weight:bold">if</span> <span style="color:#080;font-weight:bold">not</span> PY3: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">future.builtins</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">open</span> <span style="color:#777"># Specify the encoding while opening it</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">test-iso-8859-1.txt</span><span style="color:#710">&quot;</span></span>, encoding=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">ISO-8859-1</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">as</span> f: content = f.read() content = content.encode(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">UTF-8</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">replace</span><span style="color:#710">'</span></span>) print(content) </pre></div> </div> </div> <p>The two important points are</p> <ol> <li>Specifying the encoding while opening the file</li> <li>Encode the content with UTF-8</li> </ol> <p>These three little steps helped me to deal with non-UTF-8 encodings.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="https://docs.python.org/2/howto/unicode.html">Unicode HOWTO</a></li> <li><a href="https://docs.python.org/3/library/codecs.html">codecs — Codec registry and base classes</a></li> </ul> Reading and Writing Files with Python //martin-thoma.com/reading-files-with-python/ Thu, 12 Feb 2015 22:11:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/reading-files-with-python <p>Reading (and writing) files with Python is very easy. Here are some minimalistic code examples for beginners.</p> <h2 id="reading">Reading</h2> <p>A very common way to handle the contents of a file is by reading the file completely and then working with a single big string. The only reason not to do so is because your file is too big. For your information, this is how long reading a file takes (all times are in seconds, reading is executed 100 times):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>file size min max median average --------------------------------------------------- 10 KiB 0.0000 0.0008 0.0000 0.0002 100 KiB 0.0000 0.0009 0.0001 0.0002 1 MiB 0.0003 0.0013 0.0005 0.0006 10 MiB 0.0041 0.0079 0.0047 0.0049 100 MiB 0.0627 0.0778 0.0655 0.0663 </pre></div> </div> </div> <p>As you can see, reading files is quite fast. However, I would recommend the start thinking if reading the complete file is appropriate when the file size exceeds 100 MiB as you might get different problems then. For example, the content of the file might not fit in your main memory (typically 4GiB, type <code>cat /proc/meminfo | grep MemTotal</code> to get how much main memory your computer has).</p> <p>See <a href="https://gist.github.com/MartinThoma/eb1e56405009839804e7">source code</a> for details how I measured it.</p> <h3 id="completely">Completely</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">filename.txt</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> f: content = f.read() </pre></div> </div> </div> <p>is all you need to read a text file completely in a Python string variable <code>content</code>. You could, for example, split the whole string to a list of lines:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>lines = content.split(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#b0b">\n</span><span style="color:#710">'</span></span>) </pre></div> </div> </div> <h3 id="line-by-line">Line by line</h3> <p>You can read a text file line by line, but keep in mind that this will still have the endline character <code>\n</code> in each <code>line</code>!</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">filename.txt</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> f: <span style="color:#080;font-weight:bold">for</span> line <span style="color:#080;font-weight:bold">in</span> f: print(line) </pre></div> </div> </div> <h2 id="writing">Writing</h2> <p>To open files, you have to specify a mode. This is either reading, writing or appending (binary or text data). If you don’t specify it, the default value is reading. So for writing you have to specify it:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">filename.txt</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">w</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> f: f.write(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Hello world!</span><span style="color:#710">&quot;</span></span>) </pre></div> </div> </div> <h2 id="python-3">Python 3</h2> <p>Python 3 has some new features which are very nice to have. To get them in Python 2, you have to add</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">__future__</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">print_function</span> </pre></div> </div> </div> <p>at the beginning of your code before other imports happen. Now you can print to files:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">__future__</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">print_function</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">file.txt</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">w</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> f: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Hello World!</span><span style="color:#710">&quot;</span></span>, file=f) </pre></div> </div> </div> <p>The <a href="https://docs.python.org/3.0/library/functions.html#print"><code>print</code></a> function has also a “end” parameter which defaults to <code>\n</code>. This means it adds <code>\n</code> automatically at the end of each printed line. You might not want that e.g. in a Windows environment where it should be <code>\r\n</code>.</p> <h2 id="with">with</h2> <p>You might wonder what <a href="https://docs.python.org/3/reference/datamodel.html#context-managers"><code>with</code></a> does. My advice for newbees would be not to worry too much about it, it is just the way you juse I/O with Python. If you come from the C / C++ world, you might know that you have to close files when you opened them. The <code>with</code> statement makes sure that the file is closed when the block is finished.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="https://docs.python.org/3/tutorial/inputoutput.html">Python documentation: Input and Output</a></li> <li><a href="https://docs.python.org/3.0/library/functions.html#print"><code>print</code></a></li> <li><a href="https://docs.python.org/3.0/library/functions.html#open"><code>open</code></a></li> <li><a href="https://docs.python.org/3/reference/datamodel.html#context-managers"><code>with</code></a></li> <li><a href="https://docs.python.org/2/library/stdtypes.html#file-objects">File Objects</a></li> <li><a href="//martin-thoma.com/python-csv/">Python and CSV</a></li> <li><a href="//martin-thoma.com/how-to-parse-command-line-arguments-in-python/">How to parse command line arguments in Python</a></li> </ul> Python and CSV //martin-thoma.com/python-csv/ Sun, 08 Feb 2015 12:48:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-csv <p>Python has a very nice module called <a href="https://docs.python.org/3/library/csv.html"><code>csv</code></a> which makes working with <abbr title="comma seperated values">CSV</abbr> very easy. This mini article is only a reminder for me so that I can easily find how to use it when I forget once again how it is used exactly.</p> <h2 id="reading-csv-files">Reading CSV files</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">try</span>: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">future.builtins</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">open</span> <span style="color:#080;font-weight:bold">except</span>: <span style="color:#080;font-weight:bold">pass</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">csv</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">eggs.csv</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rt</span><span style="color:#710">'</span></span>, newline=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> csvfile: csvreader = csv.reader(csvfile, delimiter=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">;</span><span style="color:#710">'</span></span>, quotechar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&quot;</span><span style="color:#710">'</span></span>) <span style="color:#369;font-weight:bold">next</span>(csvreader, <span style="color:#069">None</span>) <span style="color:#777"># skip the headers</span> <span style="color:#080;font-weight:bold">for</span> row <span style="color:#080;font-weight:bold">in</span> csvreader: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">, </span><span style="color:#710">'</span></span>.join(row)) </pre></div> </div> </div> <h2 id="writing-csv-files">Writing CSV files</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">try</span>: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">future.builtins</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">open</span> <span style="color:#080;font-weight:bold">except</span>: <span style="color:#080;font-weight:bold">pass</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">csv</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">eggs.csv</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">w</span><span style="color:#710">'</span></span>, newline=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> csvfile: csvwriter = csv.writer(csvfile, delimiter=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">;</span><span style="color:#710">'</span></span>, quotechar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&quot;</span><span style="color:#710">'</span></span>, quoting=csv.QUOTE_MINIMAL) csvwriter.writerow([<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Spam</span><span style="color:#710">'</span></span>] * <span style="color:#00D">5</span> + [<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Baked Beans</span><span style="color:#710">'</span></span>]) <span style="color:#777"># Write header</span> <span style="color:#080;font-weight:bold">for</span> row <span style="color:#080;font-weight:bold">in</span> container: csvwriter.writerow(row) <span style="color:#777"># Write data</span> </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li><a href="http://stackoverflow.com/q/23051062/562769">Open files in ‘rt’ and ‘wt’ modes</a></li> <li><a href="http://stackoverflow.com/questions/tagged/python+csv?sort=votes&amp;pageSize=50">Python+CSV on StackOverflow</a></li> </ul> Python Shell autocomplete //martin-thoma.com/python-shell-autocomplete/ Thu, 05 Feb 2015 09:58:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-shell-autocomplete <p>One feature I really miss in Pythons interactive shell is tab autocompletion. Thanks to <a href="http://blog.e-shell.org/221">blog.e-shell.org</a> I know how to get it:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt;&gt; <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">rlcompleter</span>, <span style="color:#B44;font-weight:bold">readline</span> &gt;&gt;&gt; readline.parse_and_bind(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">tab:complete</span><span style="color:#710">'</span></span>) &gt;&gt;&gt; smtplib. smtplib.CRLF smtplib.__getattribute__( smtplib.LMTP smtplib.__hash__( smtplib.LMTP_PORT smtplib.__init__( smtplib.OLDSTYLE_AUTH smtplib.__name__ smtplib.SMTP smtplib.__new__( smtplib.SMTPAuthenticationError( smtplib.__package__ smtplib.SMTPConnectError( smtplib.__reduce__( smtplib.SMTPDataError( smtplib.__reduce_ex__( smtplib.SMTPException( smtplib.__repr__( smtplib.SMTPHeloError( smtplib.__setattr__( smtplib.SMTPRecipientsRefused( smtplib.__sizeof__( smtplib.SMTPResponseException( smtplib.__str__( smtplib.SMTPSenderRefused( smtplib.__subclasshook__( smtplib.SMTPServerDisconnected( smtplib._addr_only( smtplib.SMTP_PORT smtplib._have_ssl smtplib.SMTP_SSL smtplib.base64 smtplib.SMTP_SSL_PORT smtplib.email smtplib.SSLFakeFile smtplib.encode_base64( smtplib.__all__ smtplib.hmac smtplib.__class__( smtplib.quoteaddr( smtplib.__delattr__( smtplib.quotedata( smtplib.__dict__ smtplib.re smtplib.__doc__ smtplib.socket smtplib.__file__ smtplib.ssl smtplib.__format__( smtplib.stderr </pre></div> </div> </div> <p>Now if you want to always have that, you can get it by editing your <code>~/.pythonrc</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">rlcompleter</span>, <span style="color:#B44;font-weight:bold">readline</span> readline.parse_and_bind(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">tab:complete</span><span style="color:#710">'</span></span>) </pre></div> </div> </div> <p>You also have to make sure that the environment variable <code>PYTHONSTARTUP</code> is set to <code>~/.pythonrc</code>. In my case, I had to add the line <code>export PYTHONSTARTUP=~/.pythonrc</code> to <code>~/.zshrc</code>.</p> <p>I have also seen that there is another, “more powerful”, Python shell called ipython. However, I don’t understand how this shell supports autocompletion (see <a href="http://stackoverflow.com/q/28329269/562769">How does ipython3 import autocomplete work?</a>).</p> Execute Python on Apache2 //martin-thoma.com/execute-python-on-apache2/ Sun, 01 Feb 2015 15:11:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/execute-python-on-apache2 <p>I have to run a very simple Python script on an Apache2 web server. These were the steps with which I made it work:</p> <h2 id="find-the-apache2-config">Find the Apache2 config</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ /usr/sbin/apache2 -V </pre></div> </div> </div> <p>It is in <code>/etc/apache2/apache2.conf</code></p> <h2 id="add-cgi">Add CGI</h2> <p>Somewhere in the <code>/etc/apache2/apache2.conf</code> there is a <code>&lt;Directory ...&gt;</code> part. I’ve added <code>Options ExecCGI</code> and <code>AddHandler cgi-script .py</code>. Now this part looks like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&lt;Directory /var/www/&gt; Options Indexes FollowSymLinks ExecCGI AddHandler cgi-script .py AllowOverride None Require all granted &lt;/Directory&gt; </pre></div> </div> </div> <h2 id="test-it">Test it</h2> <p>Create the following <code>test.py</code> file:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: UTF-8 -*-</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Content-Type: text/html</span><span style="color:#b0b">\n</span><span style="color:#710">&quot;</span></span>) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Hello World! The answer to live, the universe and everything is %i.</span><span style="color:#710">&quot;</span></span> % (<span style="color:#00D">2</span>*<span style="color:#00D">21</span>)) </pre></div> </div> </div> <p>Now call <code>http://localhost/test.py</code>.</p> <p>If that doesn’t work, take a look at the apache log files:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ tail -f /var/log/apache2/error.log </pre></div> </div> </div> GUI programming with Python //martin-thoma.com/gui-programming-with-python/ Fri, 23 Jan 2015 14:39:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/gui-programming-with-python <p>A graphical user interface (GUI) is essential for applications which should be used by standard computer users (non-developers, not computer scientists, …). However, I have almost no experience with GUI development outside of the web.</p> <p>Multiple GUI toolkits exist and the only one I have ever used is <a href="https://en.wikipedia.org/wiki/Tk_(software)">Tk</a> for a very, very simple GUI.</p> <p>In this article, I want to share some of my thoughts about GUI development with Python as a beginner. I might update this in future.</p> <h2 id="gui-toolkits">GUI toolkits</h2> <blockquote> <p>A widget toolkit, widget library, GUI toolkit, or UX library is a library or a collection of libraries containing a set of graphical control elements (called widgets) used to construct the graphical user interface (GUI) of programs.</p> </blockquote> <p>Source: <a href="https://en.wikipedia.org/wiki/Widget_toolkit">Widget toolkit</a></p> <h2 id="comparison">Comparison</h2> <p>I am only interested in GUI toolkits</p> <ul> <li>which work on Ubuntu 12.04+,</li> <li>which have a Python binding,</li> <li>which are OpenSource and have a good license,</li> <li>which are used by others (and hence have enough documentation and examples)</li> </ul> <p>It seems to me that only the following four toolkits fulfill these requirements: GTK, Qt, Tk, wxWidgets. Some of these have multiple Python bindings and all have multiple GUI builders / designers. I tried to find the most commonly used one. Please let me know if I should add something, replace something:</p> <style> .data-table { border-collapse: collapse; } .border-bottom { border-bottom: 1px solid #000; } .border-right { border-right: 1px solid #000; } </style> <table class="data-table"> <tr> <th class="border-bottom border-right">Name</th> <th class="border-bottom"><a href="https://en.wikipedia.org/wiki/GTK%2B">GTK+</a></th> <th class="border-bottom"><a href="https://en.wikipedia.org/wiki/Qt_(software)">Qt</a></th> <th class="border-bottom"><a href="https://en.wikipedia.org/wiki/Tk_(software)">Tk</a></th> <th class="border-bottom"><a href="https://en.wikipedia.org/wiki/WxWidgets">wxWidgets</a></th> </tr> <tr> <th class="border-right">Latest version (23.01.2015)</th> <td>3.14.1</td> <td>5.4.0</td> <td>8.6.3</td> <td>3.0.2</td> </tr> <tr> <th class="border-right">Official Website</th> <td><a href="http://www.gtk.org/">gtk.org</a></td> <td><a href="https://qt-project.org/">qt-project.org</a></td> <td><a href="http://www.tcl.tk/">tcl.tk</a></td> <td><a href="http://wxwidgets.org/">wxwidgets.org</a></td> </tr> <tr> <th class="border-right">Initial release</th> <td>1998</td> <td>1995</td> <td>1991</td> <td>1992</td> </tr> <tr> <th class="border-right">Written in</th> <td>C</td> <td>C++</td> <td>C</td> <td>C++</td> </tr> <tr> <th class="border-right">Documentation</th> <td><a href="http://www.gtk.org/documentation.php">gtk.org/documentation.php</a></td> <td><a href="http://doc.qt.io/">doc.qt.io</a></td> <td><a href="http://www.tkdocs.com/">tkdocs.com</a></td> <td><a href="http://wxwidgets.org/docs/">wxwidgets.org/docs</a></td> </tr> <tr> <th class="border-right">Tutorial</th> <td><a href="https://developer.gnome.org/gtk-tutorial/stable/">developer.gnome.org/gtk-tutorial/stable</a></td> <td><a href="http://qt-project.org/doc/qt-4.8/tutorials.html">qt-project.org/doc/qt-4.8/tutorials.html</a></td> <td><a href="http://www.tkdocs.com/tutorial/index.html">tkdocs.com/tutorial</a></td> <td><a href="https://www.wxwidgets.org/docs/tutorials/">wxwidgets.org/docs/tutorials</a></td> </tr> <tr> <th class="border-right">StackOverflow questions</th> <td>4,715</td> <td>37,626</td> <td>929</td> <td>1,918</td> </tr> <tr> <td class="border-right">StackOverflow unanswered</td> <td>1,159</td> <td>9,704</td> <td>208</td> <td>429</td> </tr> <tr> <th class="border-right">License</th> <td>LGPL 2.1&nbsp;</td> <td>LGLP 3.0 (mutliple</td> <td>BSD-style</td> <td>wxWindows License</td> </tr> <tr> <th class="border-right">Python binding</th> <td>PyGTK (<a href="http://www.pygtk.org/pygtk2reference/">docs</a>)</td> <td>PySide (<a href="http://qt-project.org/wiki/PySide">docs</a>), PyQt</td> <td>Tkinter (<a href="https://docs.python.org/3/library/tkinter.html">docs</a>)</td> <td>wxPython (<a href="http://www.wxpython.org/">docs</a>)</td> </tr> <tr> <th class="border-right">Python 3 support</th> <td>yes</td> <td>yes</td> <td>yes?</td> <td>yes</td> </tr> <tr> <th class="border-right">Designer</th> <td>Glade Interface Designer</td> <td>QtDesigner, QtCreator, QDevelop, Edyuk</td> <td>SpecTcl</td> <td>wxGlade</td> </tr> <tr> <th class="border-right">Famous applications</th> <td>Gnome applications like Inkscape, <a href="https://github.com/elbersb/otr-verwaltung">OTR-Verwaltung</a></td><!-- GTK--> <td>vlc, Virtual Box, KDE applications like K3B, <a href="https://github.com/dae/anki">Anki</a></td><!-- Qt--> <td>I could not find any</td><!-- Tk--> <td>Code::Blocks<br />FileZilla<br />0 A.D.</td><!-- wxwidgets--> </tr> </table> <p>There are also some applications which use custom UI toolkits:</p> <ul> <li><a href="https://news.ycombinator.com/item?id=2822114">Sublime Text</a></li> <li><a href="https://en.wikipedia.org/wiki/Firefox">Firefox</a></li> <li><a href="http://ask.libreoffice.org/en/question/81/which-gui-toolkit-is-used-by-lo/">LibreOffice</a></li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="https://en.wikipedia.org/wiki/List_of_widget_toolkits">List of widget toolkits</a></li> <li><a href="https://en.wikipedia.org/wiki/Graphical_user_interface_builder">Graphical user interface builder</a></li> <li><a href="https://python-gtk-3-tutorial.readthedocs.org/en/latest/">The Python GTK+ 3 Tutorial</a></li> <li><a href="http://stackoverflow.com/q/349409/562769">Why are Tk GUI’s considered ugly?</a></li> <li><a href="http://stackoverflow.com/q/19584076/562769">wxPython vs PyQt vs PyGTK: when and what to use?</a></li> <li><a href="http://askubuntu.com/q/85144">What’s the difference between GTK and QT?</a></li> </ul> <p>Qt-specific</p> <ul> <li><a href="http://qt-project.org/wiki/Differences_Between_PySide_and_PyQt">Differences Between PySide and PyQt</a></li> <li><a href="http://askubuntu.com/q/140740/10425">Should I use PyQt or PySide for a new Qt project?</a></li> <li><a href="http://stackoverflow.com/q/6888750/562769">PyQt or PySide - which one to use</a></li> <li><a href="http://pythonthusiast.pythonblogs.com/230_pythonthusiast/archive/1348_developing_cross_platform_application_using_qt_pyqt_and_pyside__introduction-part_1_of_5.html">Developing Cross Platform Application using Qt, PyQt and PySide : Introduction - Part 1 of 5</a></li> </ul> Distribution of Random Variables when max gets applied //martin-thoma.com/max-distribution/ Thu, 22 Jan 2015 11:07:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/max-distribution <p>I just wanted to solve an exercise where I had random variables <code>$X_1, \dots, X_n$</code> which were all <code>$U([0, 1])$</code> distributed and <code>$Y_n = \max(X_1, \dots, X_n)$</code>.</p> <p>I wondered what the distribution of <code>$Y_n$</code> is (for big <code>$n$</code>), so I wanted to plot it. How do I plot it? With Python, of course ☺</p> <p>Here is the program:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">matplotlib.pyplot</span> <span style="color:#080;font-weight:bold">as</span> plt <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy.random</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">main</span>(): <span style="color:#777"># Generate Data</span> n = <span style="color:#00D">10000</span> numbers_a = numpy.random.uniform(size=samples) numbers_b = numpy.random.uniform(size=samples) numbers_c = numpy.random.uniform(size=samples) numbers_max = [<span style="color:#369;font-weight:bold">max</span>(a, b, c) <span style="color:#080;font-weight:bold">for</span> a, b, c <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">zip</span>(numbers_a, numbers_b, numbers_c)] <span style="color:#777"># Plot data</span> plt.hist(numbers_max) plt.title(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Histogram</span><span style="color:#710">&quot;</span></span>) plt.xlabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">value</span><span style="color:#710">&quot;</span></span>) plt.ylabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">count</span><span style="color:#710">&quot;</span></span>) plt.show() <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: main() </pre></div> </div> </div> <p>and here is the plot for <code>$n = 2$</code></p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/random-max-uniform-distribution-n-2.png"><img src="//martin-thoma.com/captions/random-max-uniform-distribution-n-2.png" alt="Plot of the maximum of 2 uniformly distributed variables with 10000 samples" width="500" height="375" class="" /></a><p class="wp-caption-text">Plot of the maximum of 2 uniformly distributed variables with 10000 samples</p></div> <p>If you increase to <code>$n = 3$</code> you get:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/random-max-uniform-distribution-n-3.png"><img src="//martin-thoma.com/captions/random-max-uniform-distribution-n-3.png" alt="Plot of the maximum of 3 uniformly distributed variables with 10000 samples" width="500" height="375" class="" /></a><p class="wp-caption-text">Plot of the maximum of 3 uniformly distributed variables with 10000 samples</p></div> <h2 id="improved-version">Improved version</h2> <p>I’ve also created an improved version which makes nicer plots, but might be harder to read:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">matplotlib.pyplot</span> <span style="color:#080;font-weight:bold">as</span> plt <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">numpy.random</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">main</span>(samples, n): <span style="color:#777"># Generate Data</span> numbers_l = [] n = n + <span style="color:#00D">1</span> <span style="color:#080;font-weight:bold">for</span> _ <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(n): numbers_l.append(numpy.random.uniform(size=samples)) <span style="color:#777"># Plot data</span> plots = [] <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">1</span>, n): <span style="color:#777"># Build data structure</span> sublist = numbers_l[:i] max_list = numbers_l[<span style="color:#00D">0</span>] <span style="color:#080;font-weight:bold">for</span> numbers_list <span style="color:#080;font-weight:bold">in</span> sublist: <span style="color:#080;font-weight:bold">for</span> i, el <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(numbers_list): max_list[i] = <span style="color:#369;font-weight:bold">max</span>(max_list[i], el) plot_i = plt.hist(max_list, histtype=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">step</span><span style="color:#710">'</span></span>, bins=<span style="color:#00D">200</span>) plots.append(plot_i) plt.title(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Histogram</span><span style="color:#710">&quot;</span></span>) plt.xlabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">value</span><span style="color:#710">&quot;</span></span>) plt.ylabel(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">count</span><span style="color:#710">&quot;</span></span>) plt.show() <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">get_parser</span>(): <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span>, <span style="color:#B44;font-weight:bold">ArgumentDefaultsHelpFormatter</span> parser = ArgumentParser(description=__doc__, formatter_class=ArgumentDefaultsHelpFormatter) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-n</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">n</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">3</span>, type=<span style="color:#369;font-weight:bold">int</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">n</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-s</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--samples</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">samples</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">1000</span>, type=<span style="color:#369;font-weight:bold">int</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">number of samples per Y_n</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">return</span> parser <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: args = get_parser().parse_args() main(args.samples, args.n) </pre></div> </div> </div> <p>When you call this script with</p> <pre><code>$ ./plot-random-variable.py -n 4 --samples 100000 </code></pre> <p>it gives</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/random-max-uniform-distribution-n-4.png"><img src="//martin-thoma.com/captions/random-max-uniform-distribution-n-4.png" alt="Plot of the maximum of 1 - 4 uniformly distributed variables with 10000 samples" width="500" height="375" class="" /></a><p class="wp-caption-text">Plot of the maximum of 1 - 4 uniformly distributed variables with 10000 samples</p></div> <h2 id="see-also">See also</h2> <ul> <li><a href="https://en.wikipedia.org/wiki/List_of_probability_distributions">List of probability distributions</a></li> <li><a href="https://bespokeblog.wordpress.com/2011/07/11/basic-data-plotting-with-matplotlib-part-3-histograms/">Basic Data Plotting with Matplotlib Part 3: Histograms</a></li> </ul> Bug Reporting - A users perspective //martin-thoma.com/bug-reporting/ Wed, 21 Jan 2015 14:54:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/bug-reporting <p>Bug reporting is extremely important. It helps developers to get aware of problems and hence get the possibility to do something against it. It is impossible to guarantee for any real, non-trivial software that it has no bugs. Even when you formally prove that it is correct, the prove might be wrong. However, when users report bugs one can get confident that the remaining bugs are appearing very rarely or causing not so much harm.</p> <p>Reporting bugs is also important from a User Experience point of view. For me, it already helps to be able to report a bug / see that a bug was already reported. However, this is a pain in the ass for most software from a users perspective.</p> <p>I’ve just had that experience for Caja (the file explorer of MATE).</p> <h2 id="caja-example">Caja example</h2> <h3 id="get-information">Get information</h3> <p>Caja crashed. I just wanted to create a new text file. Then it froze for about two seconds and closed. After another one or two seconds I got a crash report window. (I forgot to make a screenshot of that, but it looks like in the Google Chrome example)</p> <p>I clicked on something like “examine locally” - whatever that means. This is the first point I have to critize. The user should always know or at least be able to get the information what such messages mean.</p> <p>I was curious, so I clicked on it. Then this appeared:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/apport-examine-locally.png"><img src="//martin-thoma.com/captions/apport-examine-locally.png" alt="Apport 'examine locally' window" width="500" height="196" class="" /></a><p class="wp-caption-text">Apport 'examine locally' window</p></div> <blockquote> <p>This will launch apport-retrace in a terminal window to examine the crash.</p> </blockquote> <p>That is fine.</p> <blockquote> <ul> <li>Run gdb session</li> <li>Run gdb session without downloading debug symbols</li> <li>Update /var/crash/_usr_bin_caja.1000.crash with fully symbolic stack trace</li> </ul> </blockquote> <p>That is not ok. This might be good information for developers, but for normal users it is useless. There should be information when to use which one. For example:</p> <ul> <li>Which option takes most time (if there is a significant difference)?</li> <li>Is one option a superset of the other?</li> <li>Might one option contain private / secret information which I should not share?</li> </ul> <p>Lets try ‘Run gdb session’. By the way, ‘gdb’ is the GNU project debugger.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/run-gdb-session.png"><img src="//martin-thoma.com/captions/run-gdb-session.png" alt="Error creating child process" width="500" height="341" class="" /></a><p class="wp-caption-text">Error creating child process</p></div> <p>Hrmpf. Seems as if I found a bug while trying to report a bug… This happens for every option.</p> <p>Ok. Let’s see if I can report the bug. As the automatic tools did not help, I check for a program version via <em>Help &gt; About</em>:</p> <div style="width: 333px" class="wp-caption aligncenter"><a href="../images/2015/01/caja-about.png"><img src="../images/2015/01/caja-about.png" alt="Caja About window" width="" height="" class="" /></a><p class="wp-caption-text">Caja About window</p></div> <p>Nice! It is obvious which version I use and how the program is called (Caja 1.8.2). There is even a link to a website where I could eventually report the bug. It links to <a href="http://www.mate-desktop.org/">www.mate-desktop.org</a>.</p> <h3 id="report-bug">Report bug</h3> <p>When I search for ‘bug’ on <a href="http://www.mate-desktop.org/">www.mate-desktop.org</a> I get to <a href="http://www.mate-desktop.org/tr/blog/2012-01-18-reporting-bugs/">Reporting Bugs</a>. That seems to be a blog article which explains they are moving to GitHub with a link to <a href="https://github.com/mate-desktop">github.com/mate-desktop</a>. There are many repositories, so I have to search. Hrmpf. Then I get:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/caja-github.png"><img src="//martin-thoma.com/captions/caja-github.png" alt="Caja Repositories" width="500" height="566" class="" /></a><p class="wp-caption-text">Caja Repositories</p></div> <p>5 repositories. Hrmpf. I guess it is simply ‘caja’. When I click on this repository, I have to click on ‘issues’.</p> <p>Now I am stuck. I don’t know how to find a better description than “it crashed”. There is certainly more information on my system, but I don’t know how to get to it and I don’t see any instructions how to do so. I also don’t want to waste my time searching for information how to get information about the crash.</p> <h2 id="google-chrome-example">Google Chrome example</h2> <p>Just a few images…</p> <ul class="gallery mw-gallery-traditional" style="max-width: 489px; width: 489px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/01/bug-chrome-ubuntu-closed-unexpectedly.png" class="image"><img src="//martin-thoma.com/captions/bug-chrome-ubuntu-closed-unexpectedly.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 1</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/01/bug-chrome-details-1.png" class="image"><img src="//martin-thoma.com/captions/bug-chrome-details-1.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Details 1</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/01/bug-chrome-details-2-dependencies.png" class="image"><img src="//martin-thoma.com/captions/bug-chrome-details-2-dependencies.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Details 2</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/01/bug-chrome-details-3.png" class="image"><img src="//martin-thoma.com/captions/bug-chrome-details-3.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Details 3</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2015/01/bug-chrome-details-4.png" class="image"><img src="//martin-thoma.com/captions/bug-chrome-details-4.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Details 4</div></div></li></ul> <h2 id="whats-wrong-and-how-to-fix-it">What’s wrong and how to fix it</h2> <p>Did you notice how complicated this is for a user? This should be easier. In fact, I think if the bug reporting process is done right it could enhance the trust a user has in software, speed the fixing process up and help develpers to proritize what is important. Some basic steps could be:</p> <ul> <li>The automatic reporting tool should be created for non-developers.</li> <li>It should automatically store crash information in a place where the user can easily find it (e.g. /home/myaccount/.bugreports/caja/yyyy-mm-dd-hh-mm.xml)</li> <li>It should be stored in a format which the user can read (e.g. an xml file)</li> <li>The bug reporting website should be hosted by somebody else.</li> </ul> <p>Now the last one is important in my opinion. It makes sure that users know their bugs are not deleted / removed from the public just because it makes the software look bad. One could add metrics how confident users are, e.g. if you let users tell which software they use. In this case you can add graphs of how many users use the software and how many bugs / issues are reported. (The classification bugs and issues might also not be easy for users!)</p> <h2 id="existing-issue-trackers">Existing Issue Trackers</h2> <p>All of the following bug trackers seem to be developed for developers, not for users:</p> <ul> <li>Open Source Projects: <ul> <li><a href="https://en.wikipedia.org/wiki/Trac">Trac</a>: Python</li> <li><a href="https://en.wikipedia.org/wiki/Bugzilla">Bugzilla</a>: Perl</li> <li><a href="https://en.wikipedia.org/wiki/Mantis_Bug_Tracker">Mantis Bug Tracker</a>: PHP</li> <li><a href="https://en.wikipedia.org/wiki/Redmine">Redmine</a>: Ruby on Rails</li> </ul> </li> <li>Hosted Services: <ul> <li>GitHub issues (e.g. for <a href="https://github.com/numpy/numpy/issues">numpy</a>)</li> <li>Google Code (e.g. for <a href="https://code.google.com/p/chromium/issues/list">chromium</a>)</li> <li>SourceForge (e.g. for <a href="http://sourceforge.net/p/dvdstyler/bugs/?source=navbar">dvdstyler</a>)</li> <li>Launchpad (e.g. for <a href="https://bugs.launchpad.net/ubuntu">ubuntu</a>)</li> <li>GNU Savannah (e.g. for <a href="http://savannah.nongnu.org/bugs/?group=lordsawar">lordsawar</a>)</li> </ul> </li> </ul> <p>See also:</p> <ul> <li><a href="https://en.wikipedia.org/wiki/Comparison_of_source_code_software_hosting_facilities">Comparison of source code software hosting facilities</a></li> </ul> Regular Expressions with Python //martin-thoma.com/python-regex/ Tue, 20 Jan 2015 13:35:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-regex <p>Python supports regular expressions (RegEx) just as any other general purpose programming language. This mini article shows two examples how to use them.</p> <p>The package which gives RegEx support is called <a href="https://docs.python.org/3/library/re.html"><code>re</code></a>.</p> <h2 id="replacing-spaces">Replacing Spaces</h2> <p>Replace multiple whitespace characters (spaces, tabs, newlines, …) by a single space (by <a href="http://stackoverflow.com/a/1546245/562769">Nasir</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">re</span> text = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">The fox jumped over the log.</span><span style="color:#710">&quot;</span></span> replaced = re.sub(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">\s</span><span style="color:#D20">\s</span><span style="color:#D20">+</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>, text) </pre></div> </div> </div> <p>To speed things up you can also <a href="https://docs.python.org/3/library/re.html#re.compile"><code>compile</code></a> the pattern. This has also the advantage that you can specify that you want to match newline characters (<code>\n</code> and <code>\r</code>) with the dot by setting the <a href="https://docs.python.org/3/library/re.html#re.DOTALL"><code>re.DOTALL</code></a> flag.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">re</span> pattern = re.compile(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">\s</span><span style="color:#D20">\s</span><span style="color:#D20">+</span><span style="color:#710">&quot;</span></span>, re.DOTALL) text = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">The fox jumped over the log.</span><span style="color:#710">&quot;</span></span> pattern.sub(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>, text) </pre></div> </div> </div> <h2 id="unquoting">Unquoting</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">re</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">remove_quotes</span>(text): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Remove 'test'.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">unquote</span>(m): <span style="color:#080;font-weight:bold">return</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20"> %s </span><span style="color:#710">'</span></span> % <span style="color:#369;font-weight:bold">str</span>(m.group(<span style="color:#00D">1</span>)) pattern = re.compile(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> '([^ ]+?.*[^ ]+?)' </span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">return</span> pattern.sub(unquote, text) text = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">The quoted 'text piece' will get unquoted.</span><span style="color:#710">&quot;</span></span> remove_quotes(text) </pre></div> </div> </div> <h2 id="all-paragraphs">All paragraphs</h2> <p>If you want to get the content within all paragraph tags (<code>&lt;p&gt; ... &lt;/p&gt;</code> in arbitrary spacing) you can use:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">re</span> pattern = re.compile(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">&lt;p&gt;(.*?)&lt;/p&gt;</span><span style="color:#710">&quot;</span></span>, re.IGNORECASE | re.DOTALL) text = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;&quot;&quot;</span><span style="color:#D20"> </span><span style="color:#D20">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Phasellus placerat</span><span style="color:#D20"> </span><span style="color:#D20">turpis vitae malesuada tempor. Fusce cursus condimentum leo, ut bibendum justo</span><span style="color:#D20"> </span><span style="color:#D20">varius sit amet. In accumsan interdum nibh at fermentum. Nulla commodo, mi vel</span><span style="color:#D20"> </span><span style="color:#D20">ultricies efficitur, nulla tortor sagittis tortor, quis laoreet augue orci</span><span style="color:#D20"> </span><span style="color:#D20">vitae justo.</span><span style="color:#D20"> </span><span style="color:#D20"> </span><span style="color:#D20">sasdf &lt;p&gt;Suspendisse porttitor risus et est consequat condimentum.</span><span style="color:#D20"> </span><span style="color:#D20">In in eleifend ipsum, eu pulvinar nunc. Nullam vel imperdiet eros.</span><span style="color:#D20"> </span><span style="color:#D20">Phasellus vel arcu convallis, semper quam eu, convallis velit.</span><span style="color:#D20"> </span><span style="color:#D20"> </span><span style="color:#D20">&lt;/p&gt;</span><span style="color:#D20"> </span><span style="color:#D20"> </span><span style="color:#D20"> </span><span style="color:#D20">&lt;P&gt;Sed tempus magna quis neque varius aliquam. Quisque maximus et augue non</span><span style="color:#D20"> </span><span style="color:#D20">dapibus. Nullam et ante imperdiet, fringilla diam nec, mattis quam.&lt;/p&gt;</span><span style="color:#D20"> </span><span style="color:#D20"> </span><span style="color:#D20">&lt;P&gt;Ut fermentum lacus id semper imperdiet. Donec et purus consectetur,</span><span style="color:#D20"> </span><span style="color:#D20">fermentum mi nec, viverra dolor. Quisque posuere ultricies leo et efficitur.</span><span style="color:#D20"> </span><span style="color:#D20">Aliquam venenatis quis mi ac tempus.&lt;/p&gt;</span><span style="color:#D20"> </span><span style="color:#D20"> </span><span style="color:#D20">Maecenas in nisl lacinia, finibus velit eu, aliquet elit. Morbi orci libero,</span><span style="color:#D20"> </span><span style="color:#D20">interdum id vehicula vitae, &lt;p&gt;congue vel&lt;/p&gt;p&gt; lectus. Morbi lobortis eros</span><span style="color:#D20"> </span><span style="color:#D20">mollis, cursus velit at, convallis dolor. Nullam volutpat neque at risus</span><span style="color:#D20"> </span><span style="color:#D20">porttitor, faucibus tristique tellus suscipit. In sed purus quis sem tincidunt</span><span style="color:#D20"> </span><span style="color:#D20">lobortis. Vivamus ut blandit erat, sed sollicitudin felis. Etiam placerat,</span><span style="color:#D20"> </span><span style="color:#D20">sapien et vulputate placerat, mi lectus tristique nisi, vitae finibus tellus</span><span style="color:#D20"> </span><span style="color:#D20">nisi a massa. Nullam sit amet scelerisque lectus. Fusce porta justo ac</span><span style="color:#D20"> </span><span style="color:#D20">scelerisque auctor. Integer vestibulum tellus at quam molestie dapibus.</span><span style="color:#D20"> </span><span style="color:#D20">Suspendisse quis quam tortor. Nullam consequat tempus orci eget scelerisque. Ut</span><span style="color:#D20"> </span><span style="color:#D20">auctor lorem enim, id rutrum eros congue varius. In justo lacus, molestie vitae</span><span style="color:#D20"> </span><span style="color:#D20">nibh eu, venenatis auctor ex.</span><span style="color:#D20"> </span><span style="color:#710">&quot;&quot;&quot;</span></span> matches = pattern.findall(text) </pre></div> </div> </div> <p>Matches is the following list (breaked at some points for easier reading):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>['Suspendisse porttitor risus et est consequat condimentum.\n In in eleifend ipsum, eu pulvinar nunc. Nullam vel imperdiet eros.\n Phasellus vel arcu convallis, semper quam eu, convallis velit.\n\n', 'Sed tempus magna quis neque varius aliquam. Quisque maximus et augue non\n dapibus. Nullam et ante imperdiet, fringilla diam nec, mattis quam.', 'Ut fermentum lacus id semper imperdiet. Donec et purus consectetur,\n fermentum mi nec, viverra dolor. Quisque posuere ultricies leo et efficitur.\n Aliquam venenatis quis mi ac tempus.', 'congue vel'] </pre></div> </div> </div> Analyzing PyPI Metadata //martin-thoma.com/analyzing-pypi-metadata/ Sun, 18 Jan 2015 20:19:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/analyzing-pypi-metadata <div class="info">This is part one of a series. See <a href="//martin-thoma.com/analyzing-pypi-metadata-2/">Analyzing PyPI Data - 2</a> for part two.</div> <p>PyPI, the Python Package Index, gives a very crappy but simple interface to query metadata about its packages. I scrapped all of the packages metadata. 53,533 packages were scrapped (date: 2015-01-18), because I wanted to see if there is malware on PyPI (related to <a href="http://security.stackexchange.com/q/79326/3286">this question on security.SE</a>).</p> <p>The database looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/pypi-metadata-db.png"><img src="//martin-thoma.com/captions/pypi-metadata-db.png" alt="PyPI metadata database schema" width="500" height="374" class="" /></a><p class="wp-caption-text">PyPI metadata</p></div> <h2 id="exploring-the-data">Exploring the data</h2> <p>When I scapped the data from PyPI, I made all database fields “varchar 255” as there seems to be no information about the possible values. Then I explored the data</p> <ul> <li><code>name</code>: The longest package name is 80 characters long (<code>Aaaaaaaaaaa...</code>), the shortest packages have only one character.</li> <li><code>author</code>: 911× “UNKOWN”, 741× empty, 195× “None”, 151× “Zope Foundation and Contributors”. There are about 22,000 different authors. There are 595 authors who wrote more than 10 packages.</li> <li><code>author_email</code>: 2059× “UNKOWN”, 932× empty, 323× “zope-dev@zope.org”, 216× “None” and 204× “TODO”.</li> <li><code>maintainer</code>: 46879× “None”, 5507× empty, 17× <a href="http://www.boddie.org.uk/paul/CV.html">Paul Boddie</a>.</li> <li><code>requires_python</code>: 53467× “None”, 3× “UNKNOWN”, 2× “&gt;=2.7,!=3.0,!=3.1”, 2× “&gt;=2.5”, 1× “2.6”, 1× “&gt;= 3.3”, 1× “&gt;=2.4”, 1× “&gt;= 2.7” - that’s it. No other values. Seems as if this is pretty much useless.</li> <li><code>docs_url</code>: Either begins with <code>http://pythonhosted.org</code> or is empty.</li> </ul> <h3 id="most-active-authors">Most active authors</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">author</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">as</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">created_packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">author</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">author</span><span style="color:#710">`</span></span> <span style="color:#088;font-weight:bold">ASC</span> LIMIT <span style="color:#00D">50</span> </pre></div> </div> </div> <p>gives</p> <table> <thead> <tr> <th> </th> <th>1485</th> </tr> </thead> <tbody> <tr> <td>UNKNOWN</td> <td>1150</td> </tr> <tr> <td>None</td> <td>196</td> </tr> <tr> <td>OpenStack</td> <td>188</td> </tr> <tr> <td>Zope Foundation and Contributors</td> <td>146</td> </tr> <tr> <td>MicroPython Developers</td> <td>139</td> </tr> <tr> <td>OpenERP SA</td> <td>137</td> </tr> <tr> <td>Zope Corporation and Contributors</td> <td>128</td> </tr> <tr> <td>RedTurtle Technology</td> <td>127</td> </tr> <tr> <td>Praekelt Foundation</td> <td>126</td> </tr> <tr> <td>Fanstatic Developers</td> <td>98</td> </tr> <tr> <td>Tryton</td> <td>98</td> </tr> <tr> <td>Raptus AG</td> <td>97</td> </tr> <tr> <td>russianidiot</td> <td>93</td> </tr> <tr> <td>hfpython</td> <td>92</td> </tr> <tr> <td>LOGILAB S.A. (Paris, FRANCE)</td> <td>88</td> </tr> <tr> <td>BlueDynamics Alliance</td> <td>87</td> </tr> <tr> <td>Ralph Bean</td> <td>83</td> </tr> <tr> <td>JeanMichel FRANCOIS aka toutpt</td> <td>69</td> </tr> <tr> <td>Bart Thate</td> <td>68</td> </tr> </tbody> </table> <p>The total number of authors is 28 183 (06.12.2015):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="color:#080;font-weight:bold">DISTINCT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">author</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">AS</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">total_authors</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> </pre></div> </div> </div> <h3 id="maximum-length">Maximum Length</h3> <p>I guess many values are stored on PyPI as <code>Varchar(255)</code>. To check if I might have missed some values, I checked which entry was the longest one for all columns. I did this with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, LENGTH(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> LENGTH(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> </pre></div> </div> </div> <table> <tr> <th>Column</th> <th>Maximum Length</th> <th>Entry</th> </tr> <tr> <td>name</td> <td>80</td> <td>Aaaaaaaaaaaaaaaaaaa-aaaaaaaaa-aaaaaaasa-aaaaaaasa-aaaaasaa-aaaaaaasa-bbbbbbbbbbb</td> </tr> <tr> <td>author</td> <td>248</td> <td>Michael R. Crusoe, Greg Edvenson, Jordan Fish, Adina Howe, Luiz Irber, Eric McDonald, Joshua Nahum, Kaben Nanlohy, Humberto Ortiz-Zuazaga, Jason Pell, Jared Simpson, Camille Scott, Ramakrishnan Rajaram Srinivasan, Qingpeng Zhang, and C. Titus Brown</td> </tr> <tr> <td>author_email</td> <td>215</td> <td>ongsp@ucsd.edu, anubhavj@mit.edu, mpkocher@lbnl.gov, geoffroy.hautier@uclouvain.be, wrichard@mit.edu, sdacek@mit.edu, dkgunter@lbl.gov, scholia@lbl.gov, gmatteo@gmail.com, vincentchevrier@gmail.com, armiento@mit.edu</td> </tr> <tr> <td>maintainer</td> <td>63</td> <td>Panagiotis Liakos, Katia Papakonstantinopoulou, Michael Sioutis</td> </tr> <tr> <td>maintainer_email</td> <td>67</td> <td>maxistedeams@gmail.com, p_riendeau@live.ca, rheault.etccy@gmail.com</td> </tr> <tr> <td>requires_python</td> <td>17</td> <td>&gt;=2.7,!=3.0,!=3.1</td> </tr> <tr> <td>platform</td> <td>231</td> <td>Natural Language :: English<br />License :: OSI Approved :: Apache Software License<br />Environment :: Console<br />Development Status :: 2 - Pre-Alpha<br />Intended Audience :: Developers<br />Programming Language :: Python :: 2.7<br />Topic :: Database</td> </tr> <tr> <td>version</td> <td>73</td> <td>[In Progress] Python middle layer for interacting with Redis data easily.</td> </tr> <tr> <td>license</td> <td>466</td> <td>Copyright &copy; 2014 &#1047;&#1040;&#1054; &ldquo;&#1041;&#1040;&#1056;&#1057; &#1043;&#1088;&#1091;&#1087;&rdquo;<br /><br />&#1044;&#1072;&#1085;&#1085;&#1072;&#1103; &#1083;&#1080;&#1094;&#1077;&#1085;&#1079;&#1080;&#1103; &#1088;&#1072;&#1079;&#1088;&#1077;&#1096;&#1072;&#1077;&#1090; &#1083;&#1080;&#1094;&#1072;&#1084;, &#1087;&#1086;&#1083;&#1091;&#1095;&#1080;&#1074;&#1096;&#1080;&#1084; &#1082;&#1086;&#1087;&#1080;&#1102; &#1076;&#1072;&#1085;&#1085;&#1086;&#1075;&#1086; &#1087;&#1088;&#1086;&#1075;&#1088;&#1072;&#1084;&#1084;&#1085;&#1086;&#1075;&#1086; &#1086;&#1073;&#1077;&#1089;&#1087;&#1077;&#1095;&#1077;&#1085;&#1080;&#1103; &#1080; &#1089;&#1086;&#1087;&#1091;&#1090;&#1089;&#1090;&#1074;&#1091;&#1102;&#1097;&#1077;&#1081; &#1076;&#1086;&#1082;&#1091;&#1084;&#1077;&#1085;&#1090;&#1072;&#1094;&#1080;&#1080; (&#1074; &#1076;&#1072;&#1083;&#1100;&#1085;&#1077;&#1081;&#1096;&#1077;&#1084;<br />&#1080;&#1084;&#1077;&#1085;&#1091;&#1077;&#1084;&#1099;&#1084;&#1080; &laquo;&#1055;&#1088;&#1086;&#1075;&#1088;&#1072;&#1084;&#1084;&#1085;&#1086;&#1077; &#1054;&#1073;&#1077;&#1089;&#1087;&#1077;&#1095;&#1077;&#1085;&#1080;&#1077;&raquo;), &#1073;&#1077;&#1079;&#1074;&#1086;&#1079;&#1084;&#1077;&#1079;&#1076;&#1085;&#1086; &#1080;&#1089;&#1087;&#1086;&#1083;&#1100;&#1079;&#1086;&#1074;&#1072;&#1090;&#1100; &#1055;&#1088;&#1086;&#1075;&#1088;&#1072;&#1084;&#1084;&#1085;&#1086;&#1077; &#1054;&#1073;&#1077;&#1089;&#1087;&#1077;&#1095;&#1077;&#1085;&#1080;&#1077; &#1073;&#1077;&#1079; &#1086;&#1075;</td> </tr> <tr> <td>keywords</td> <td>655</td> <td>ArcLink,array,array analysis,ASC,beachball,beamforming,cross correlation,database,dataless,Dataless SEED,datamark,earthquakes,Earthworm,EIDA,envelope,events,FDSN,features,filter,focal mechanism,GSE1,GSE2,hob,iapsei-tau,imaging,instrument correction,instrument simulation,IRIS,magnitude,MiniSEED,misfit,mopad,MSEED,NERA,NERIES,observatory,ORFEUS,picker,processing,PQLX,Q,real time,realtime,RESP,response file,RT,SAC,SEED,SeedLink,SEG-2,SEG Y,SEISAN,SeisHub,Seismic Handler,seismology,seismogram,seismograms,signal,slink,spectrogram,StationXML,taper,taup,travel time,trigger,VERCE,WAV,waveform,WaveServer,WaveServerV,WebDC,web service,Winston,XML-SEED,XSEED</td> </tr> <tr> <td>description</td> <td>65535</td> <td>[id don't want to put that here - there were 22 with this length]</td> </tr> <tr> <td>summary</td> <td>278</td> <td>Splits one vcard file (*.vcf) to many vcard files &nbsp; &nbsp; &nbsp; &nbsp;with one vcard per file. Useful for import contacts to phones, &nbsp; &nbsp; &nbsp; &nbsp; thats do not support multiple vcard in one file. &nbsp; &nbsp; &nbsp; &nbsp; Supprt unicode cyrillic characters. &nbsp; &nbsp; &nbsp; &nbsp; &#1050;&#1086;&#1085;&#1089;&#1086;&#1083;&#1100;&#1085;&#1072;&#1103; &#1087;&#1088;&#1086;&#1075;&#1088;&#1072;&#1084;&#1084;&#1072; &#1076;&#1083;&#1103; &#1088;</td> </tr> <tr> <td>stable_version</td> <td>4</td> <td>None</td> </tr> <tr> <td>home_page</td> <td>134</td> <td>http://127.0.0.1:8888/USK@9X7bw5HD2ufYvJuL3qAVsYZb3KbI9~FyRu68zsw5HVg,lhHkYYluqHi7BcW1UHoVAMcRX7E5FaZjWCOruTspwQQ,AQACAAE/pyfcp-api/0/</td> </tr> <tr> <td>release_url</td> <td>130</td> <td>http://pypi.python.org/pypi/softwarefabrica.django.appserver/1.0dev-BZR-r10-panta-elasticworld.org-20091023132843-vitk6k7e5qlvhej5</td> </tr> <tr> <td>bugtrack_url</td> <td>104</td> <td>https://bugzilla.redhat.com/buglist.cgi?submit&amp;component=python-nss&amp;product=Fedora&amp;classification=Fedora</td> </tr> <tr> <td>download_url</td> <td>183</td> <td>http://pypi.python.org/packages/source/s/softwarefabrica.django.appserver/softwarefabrica.django.appserver-1.0dev-BZR-r10-panta-elasticworld.org-20091023132843-vitk6k7e5qlvhej5.tar.gz</td> </tr> <tr> <td>package_url</td> <td>108</td> <td>http://pypi.python.org/pypi/Aaaaaaaaaaaaaaaaaaa-aaaaaaaaa-aaaaaaasa-aaaaaaasa-aaaaasaa-aaaaaaasa-bbbbbbbbbbb</td> </tr> <tr> <td>_pypi_hidden</td> <td>-</td> <td>True or False</td> </tr> <tr> <td>_pypi_ordering</td> <td>-</td> <td>Integers from 0 to 464</td> </tr> <tr> <td>cheesecake_code_kwalitee_id</td> <td>-</td> <td>Integers from 183 to 6513 and None values</td> </tr> <tr> <td>cheesecake_documentation_id</td> <td>-</td> <td>Integers from 182 to 6512 and None values</td> </tr> <tr> <td>cheesecake_installability_id</td> <td>-</td> <td>Integers from 181 to 6511 and None values</td> </tr> </table> <p>We can see multiple problems here:</p> <ul> <li>URLs: localhost / 127.0.0.1 is almost certainly not desired</li> <li><code>cheesecake_installability_id</code>, <code>cheesecake_documentation_id</code>, <code>cheesecake_code_kwalitee_id</code> should have NULL and None should be casted to NULL. The data type is likely to be numeric.</li> <li><code>_pypi_ordering</code> should be numeric</li> <li><code>_pypi_hidden</code> should be boolean</li> </ul> <p>So I changed the types in the database. Let’s continue.</p> <h2 id="what-people-dont-use">What people don’t use</h2> <p>All metadata is provided by the authors of the packages. Some fields, like the package name or the description, are used very often, but some fields are only rarely used:</p> <h3 id="maintainer">Maintainer</h3> <p><code>maintainer</code> and <code>maintainer_email</code> is interesting for people who want to send bug reports. If this is empty, I would guess the package is dead.</p> <h3 id="platform">Platform</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">platform</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">platform</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> </pre></div> </div> </div> <p>gives 759 different results. The TOP-10 were</p> <table> <thead> <tr> <th>Platform</th> <th>Count</th> </tr> </thead> <tbody> <tr> <td>UNKNOWN</td> <td>43539</td> </tr> <tr> <td>any</td> <td>3515</td> </tr> <tr> <td> </td> <td>1986</td> </tr> <tr> <td>Any</td> <td>635</td> </tr> <tr> <td>OS Independent</td> <td>542</td> </tr> <tr> <td>None</td> <td>265</td> </tr> <tr> <td>Linux</td> <td>225</td> </tr> <tr> <td>linux</td> <td>167</td> </tr> <tr> <td>Posix; MacOS X; Windows</td> <td>157</td> </tr> <tr> <td>POSIX</td> <td>156</td> </tr> </tbody> </table> <p>You can see that there are alternative ways to express the same thing. Also, the “;” should not be here as the manual states it should be a list.</p> <p><a href="https://docs.python.org/2/distutils/setupscript.html">The manual</a> is also too short for this entry. It only says “a list of platforms” which seems to be pretty much useless.</p> <p><a href="http://docstore.mik.ua/orelly/other/python/0596001886_pythonian-chp-26-sect-1.html">docstore.mik.ua</a> gives a little bit more information</p> <blockquote> <p>A list of platforms on which this distribution is known to work. You should provide this information if you have reasons to believe this distribution may not work everywhere. This information should be reasonably concise, so this field may refer for details to a file in the distribution or to a URL.</p> </blockquote> <h3 id="bugtracker">Bugtracker</h3> <p>This one is very important. Users should have an easy possibility to report bugs. So please help them by added your bug tracker URL wherever it makes sense. Here is how you add it on PyPI:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/pypi-bugtrack-url.png"><img src="//martin-thoma.com/captions/pypi-bugtrack-url.png" alt="Go to your packages PyPI page" width="500" height="263" class="" /></a><p class="wp-caption-text">Go to your packages PyPI page</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/pypi-add-bugtrack-url.png"><img src="//martin-thoma.com/captions/pypi-add-bugtrack-url.png" alt="Add your bugtracker / issue tracker url" width="500" height="408" class="" /></a><p class="wp-caption-text">Add your bugtracker / issue tracker url</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/pypi-added-bugtracker.png"><img src="//martin-thoma.com/captions/pypi-added-bugtracker.png" alt="Check if you really added it" width="500" height="271" class="" /></a><p class="wp-caption-text">Check if you really added it</p></div> <h3 id="license">License</h3> <p>Another important one. Add a license to your software!</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">license</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> packages <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">license</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> </pre></div> </div> </div> <p>gives</p> <table> <thead> <tr> <th>License</th> <th>Count</th> </tr> </thead> <tbody> <tr> <td>UNKNOWN</td> <td>11444</td> </tr> <tr> <td>MIT</td> <td>8098</td> </tr> <tr> <td>BSD</td> <td>7224</td> </tr> <tr> <td>GPL</td> <td>4202</td> </tr> <tr> <td>MIT License</td> <td>1410</td> </tr> <tr> <td>(empty)</td> <td>1398</td> </tr> <tr> <td>LICENSE.txt</td> <td>1201</td> </tr> <tr> <td>GPLv3</td> <td>1083</td> </tr> <tr> <td>LGPL</td> <td>833</td> </tr> <tr> <td>ZPL 2.1</td> <td>829</td> </tr> <tr> <td>BSD License</td> <td>811</td> </tr> <tr> <td>Apache License 2.0</td> <td>482</td> </tr> <tr> <td>Apache License, Version 2.0</td> <td>443</td> </tr> <tr> <td>Apache 2.0</td> <td>437</td> </tr> <tr> <td>GPLv2</td> <td>370</td> </tr> <tr> <td>None</td> <td>363</td> </tr> <tr> <td>ZPL</td> <td>288</td> </tr> <tr> <td>GPL-3</td> <td>272</td> </tr> <tr> <td>GPLv3+</td> <td>258</td> </tr> <tr> <td>LICENSE</td> <td>249</td> </tr> </tbody> </table> <p>and about 6500 other licenses. Most might be variants in writing, e.g.</p> <ul> <li>Apache License 2.0</li> <li>Apache License, Version 2.0</li> <li>Apache 2.0</li> </ul> <p>are all the same license. Some packages have no licence (<code>Unknown</code> and empty). Many are invalid values, like</p> <ul> <li>LICENSE.txt</li> <li>None</li> <li>LICENSE</li> <li>Python</li> </ul> <p>These indicate that people have no idea what to input there. <a href="https://tldrlegal.com/">tldrlegal.com</a> might help in that case. I think the Python community should try to eliminate variants in writing license names as it makes finding, filtering and analyzing packages more difficult.</p> <h2 id="classifiers">Classifiers</h2> <p>Python makes use of so called trove classifiers. They are defined in <a href="https://www.python.org/dev/peps/pep-0301/#distutils-trove-classification">PEP 301</a> and listed <a href="https://pypi.python.org/pypi?%3Aaction=list_classifiers">here</a>.</p> <p>The following table gives the TOP-10 most commonly used classifiers:</p> <table> <thead> <tr> <th>Classifier</th> <th>Percentage</th> </tr> </thead> <tbody> <tr> <td>Programming Language :: Python</td> <td>0.4615</td> </tr> <tr> <td>Intended Audience :: Developers</td> <td>0.4412</td> </tr> <tr> <td>Operating System :: OS Independent</td> <td>0.3229</td> </tr> <tr> <td>Programming Language :: Python :: 2.7</td> <td>0.2183</td> </tr> <tr> <td>Topic :: Software Development :: Libraries :: Pyth…</td> <td>0.2038</td> </tr> <tr> <td>Development Status :: 4 - Beta</td> <td>0.2038</td> </tr> <tr> <td>License :: OSI Approved :: BSD License</td> <td>0.1632</td> </tr> <tr> <td>License :: OSI Approved :: MIT License</td> <td>0.1529</td> </tr> <tr> <td>Environment :: Web Environment</td> <td>0.1487</td> </tr> <tr> <td>Programming Language :: Python :: 2.6</td> <td>0.1306</td> </tr> </tbody> </table> <p>When you analyze the licenses with the trove classifiers you get a different image:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">classifier</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) / <span style="color:#00D">53533</span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">package_classifiers</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">classifier</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">LIKE</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">License%</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">classifier</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> </pre></div> </div> </div> <table> <thead> <tr> <th>License</th> <th>Percentage</th> </tr> </thead> <tbody> <tr> <td>License :: OSI Approved :: BSD License</td> <td>0.1632</td> </tr> <tr> <td>License :: OSI Approved :: MIT License</td> <td>0.1529</td> </tr> <tr> <td>License :: OSI Approved :: GNU General Public License (GPL)</td> <td>0.0625</td> </tr> <tr> <td>License :: OSI Approved :: Apache Software License</td> <td>0.0460</td> </tr> <tr> <td>License :: OSI Approved :: GNU Library or Lesser General Public License (LGPL)</td> <td>0.0188</td> </tr> </tbody> </table> <p>There are 94 trove classifiers with five or less packages which use this classifier. I guess many of them are not in the official list of classifiers.</p> <h2 id="package-type">Package type</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packagetype</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">urls</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> packagetype <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">COUNT</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> </pre></div> </div> </div> <p>gives</p> <table> <thead> <tr> <th>Package type</th> <th>Count</th> </tr> </thead> <tbody> <tr> <td>sdist</td> <td>47649</td> </tr> <tr> <td>bdist_egg</td> <td>4933</td> </tr> <tr> <td>bdist_wheel</td> <td>3098</td> </tr> <tr> <td>bdist_wininst</td> <td>1512</td> </tr> <tr> <td>bdist_dumb</td> <td>577</td> </tr> <tr> <td>bdist_msi</td> <td>45</td> </tr> <tr> <td>bdist_rpm</td> <td>35</td> </tr> <tr> <td>bdist_dmg</td> <td>4</td> </tr> </tbody> </table> <p>Can anybody explain what this means?</p> <h2 id="downloads">Downloads</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">url</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">downloads</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">urls</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">urls</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">package_id</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">urls</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">downloads</span><span style="color:#710">`</span></span> <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">10</span> </pre></div> </div> </div> <p>gives</p> <table> <thead> <tr> <th>Package type</th> <th>Count</th> </tr> </thead> <tbody> <tr> <td><a href="https://pypi.python.org/pypi/wincertstore">wincertstore</a></td> <td>10026403</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/ssl">ssl</a></td> <td>8987455</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/pyasn1">pyasn1</a></td> <td>8655361</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/Paste">Paste</a></td> <td>8401111</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/PyYAML">PyYAML</a></td> <td>7180547</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/distribute">distribute</a></td> <td>6276421</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/MarkupSafe">MarkupSafe</a></td> <td>6215382</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/ecdsa">ecdsa</a></td> <td>6030395</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/meld3">meld3</a></td> <td>5715687</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/pika">pika</a></td> <td>5567400</td> </tr> </tbody> </table> <p>and</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="color:#369;font-weight:bold">SUM</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">downloads</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">releases</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">releases</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">package_id</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">GROUP</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="color:#369;font-weight:bold">SUM</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">downloads</span><span style="color:#710">`</span></span>) <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">10</span> </pre></div> </div> </div> <table> <thead> <tr> <th>Package type</th> <th>Count</th> </tr> </thead> <tbody> <tr> <td><a href="https://pypi.python.org/pypi/setuptools">setuptools</a></td> <td>45485205</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/requests">requests</a></td> <td>35446321</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/virtualenv">virtualenv</a></td> <td>35039299</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/distribute">distribute</a></td> <td>34779943</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/boto">boto</a></td> <td>29678066</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/six">six</a></td> <td>28253705</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/certifi">certifi</a></td> <td>27381407</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/pip">pip</a></td> <td>26266325</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/wincertstore">wincertstore</a></td> <td>24831145</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/lxml">lxml</a></td> <td>20901298</td> </tr> </tbody> </table> <h2 id="size">Size</h2> <p>What is the biggest Python package?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">name</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">release_number</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">size</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">releases</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">JOIN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ON</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">releases</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">package_id</span><span style="color:#710">`</span></span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">packages</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">ORDER</span> <span style="color:#080;font-weight:bold">BY</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">releases</span><span style="color:#710">`</span></span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">size</span><span style="color:#710">`</span></span> <span style="color:#088;font-weight:bold">DESC</span> LIMIT <span style="color:#00D">30</span> </pre></div> </div> </div> <table> <thead> <tr> <th>Package</th> <th>Version</th> <th>Size</th> </tr> </thead> <tbody> <tr> <td><a href="https://pypi.python.org/pypi/de422">de422</a></td> <td>2009.1</td> <td>545298406</td> </tr> <tr> <td>de406</td> <td>1997.1</td> <td>178260546</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/scipy">scipy</a></td> <td>0.13.3</td> <td>62517637</td> </tr> <tr> <td>appdynamics-bindeps-linux-x86</td> <td>5913-master</td> <td>57861536</td> </tr> <tr> <td>appdynamics-bindeps-linux-x64</td> <td>5913-master</td> <td>56366211</td> </tr> <tr> <td>python-qt5</td> <td>0.1.5</td> <td>56259023</td> </tr> <tr> <td>python-qt5</td> <td>0.1.8</td> <td>56237972</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/pycalculix">pycalculix</a></td> <td>0.92</td> <td>56039839</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/wltp">wltp</a></td> <td>0.0.9-alpha.3</td> <td>55414544</td> </tr> <tr> <td><a href="https://pypi.python.org/pypi/cefpython3">cefpython3</a></td> <td>31.2</td> <td>55163815</td> </tr> </tbody> </table> <h2 id="code">Code</h2> <p>See <a href="https://github.com/MartinThoma/algorithms/tree/master/PyPI">github.com/MartinThoma/algorithms</a>.</p> <h2 id="related">Related</h2> <ul> <li><a href="http://stackoverflow.com/q/28010799/562769">Why are some packages on pypi.python.org/simple, but have no page?</a></li> <li><a href="http://www.quora.com/How-can-I-find-out-when-the-last-interaction-on-PyPI-happened-for-a-given-package">How can I find out when the last interaction on PyPI happened for a given package?</a></li> <li><a href="http://www.quora.com/What-is-cheesecake_code_kwalitee_id-on-PyPI-good-for">What is cheesecake_code_kwalitee_id on PyPI good for?</a></li> </ul> <h2 id="further-ideas">Further Ideas</h2> <ul> <li><strong>Build a dependency graph</strong>: Some of the code was already written. However, one has to download about 25 GB of data, extract it and run over those files. This is quite a bit of work.</li> <li>Analyze package quality <ul> <li>Missing requirements</li> <li>Missing metadata / description</li> <li>Missing documentation</li> <li>PEP8</li> <li>Code duplication</li> </ul> </li> <li>Malicious package search: <ul> <li>Check which package names are prefixes of other package names.</li> <li>Find packages which upload data (dropbox?)</li> <li>Find pacakges which remove data from your file system</li> </ul> </li> </ul> LaTeX and tables //martin-thoma.com/latex-tables/ Tue, 30 Dec 2014 21:57:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/latex-tables <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>LaTeX is an awesome typesetting language: It is powerful enough to let you do anything you want, it has a great community and standard solutions for every common problem as it is quite old. But tables… well, let’s say there is much room for improvement.</p> <h2 id="how-to-make-tables">How to make tables</h2> <h3 id="the-simple-way">The simple way</h3> <p>The most basic table I could think of is generated like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper]{scrartcl} \usepackage{amssymb, amsmath} % needed for math \begin{document} Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis malesuada efficitur volutpat. Proin eget dui in lacus fermentum pharetra. Sed ut facilisis leo, sed consectetur urna. Phasellus eget tempus eros, vitae sagittis mi. Nullam pharetra, dolor a efficitur blandit, nisl velit interdum turpis, vel posuere lorem justo nec elit. Donec mattis massa auctor mattis varius. Nunc sed volutpat sapien, at finibus lectus. Phasellus auctor vehicula auctor. Nam vitae purus ut orci accumsan auctor. Fusce volutpat, tortor consectetur convallis aliquam, enim velit gravida sapien, id convallis nisi nunc ac leo. \begin{table}[ht] \centering \begin{tabular}{l|rrr} Country / Property &amp; Population &amp; Area &amp; HDI \\\hline France &amp; $66 \cdot 10^6$ &amp; $668763\text{km}^2$ &amp; 0.89 \\ Germany &amp; $81 \cdot 10^6$ &amp; $357167\text{km}^2$ &amp; 0.92 \\ United States &amp; $317 \cdot 10^6$ &amp; $9629091\text{km}^2$ &amp; 0.94 \\ \end{tabular} \caption{Information about countries} \label{table:countries} \end{table} Aenean sit amet felis eu urna accumsan consectetur. Sed hendrerit ultrices turpis nec fringilla. Pellentesque sagittis neque placerat, pharetra ante quis, maximus eros. Nam ultrices lacinia magna, eget interdum tortor ornare ut. Praesent semper tristique consectetur. Sed auctor, orci accumsan imperdiet vestibulum, nunc augue sagittis purus, sed dapibus neque arcu sit amet enim. Aliquam fermentum dui eu efficitur condimentum. Maecenas viverra metus ut bibendum pellentesque. Integer non interdum massa. Vestibulum non enim vulputate, sodales nunc ac, ultricies tortor. Suspendisse non vehicula ipsum, quis consequat elit. Quisque rutrum tincidunt lorem id semper. Phasellus bibendum nulla sit amet purus tempus, vitae tincidunt ligula ornare. Nunc quis felis non ex consequat elementum nec sit amet magna. In lacinia nulla nec neque venenatis, vel tristique risus blandit. \end{document} </pre></div> </div> </div> <p>It will look like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/09/latex-standard-table.png"><img src="//martin-thoma.com/captions/latex-standard-table.png" alt="Standard LaTeX table" width="500" height="217" class="" /></a><p class="wp-caption-text">Standard LaTeX table</p></div> <p>You can see two environments: <code>table</code> and <code>tabular</code>. Let’s focus on <code>tabular</code> first. It is always followed by a list of characters <code>l</code>, <code>c</code>, <code>r</code> which define if the column is left-aligned, centered or right-aligned. You can add <code>|</code> to tell LaTeX if there should be a line to distinguish columns. After that you get to the first cells. <code>&amp;</code> starts a new cell and <code>\\</code> starts a new line. If you want a drawn line / rule, you can use <code>\hline</code>.</p> <p>Let’s check out <code>table</code>: <code>table</code> has options after it which are commonly <code>ht</code> where <code>h</code> means “here” and <code>t</code> means “top”. So LaTeX tries to place the table where it is in the text and if that doesn’t work out it places the table on the top of the page. It can get a caption <code>\caption{Description of the contents of the table}</code> and a <code>\label{table:your-label-for-internal-usage}</code>.</p> <h3 id="the-standard-way">The standard way</h3> <p>I always use <code>\usepackage{booktabs}</code> to get <code>\toprule</code>, <code>\midrule</code> and <code>\bottomrule</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper]{scrartcl} \usepackage{amssymb, amsmath} % needed for math \usepackage{booktabs} % for \toprule, \midrule and \bottomrule \begin{document} Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis malesuada efficitur volutpat. Proin eget dui in lacus fermentum pharetra. Sed ut facilisis leo, sed consectetur urna. Phasellus eget tempus eros, vitae sagittis mi. Nullam pharetra, dolor a efficitur blandit, nisl velit interdum turpis, vel posuere lorem justo nec elit. Donec mattis massa auctor mattis varius. Nunc sed volutpat sapien, at finibus lectus. Phasellus auctor vehicula auctor. Nam vitae purus ut orci accumsan auctor. Fusce volutpat, tortor consectetur convallis aliquam, enim velit gravida sapien, id convallis nisi nunc ac leo. \begin{table}[ht] \centering \begin{tabular}{l|rrr} \toprule Country / Property &amp; Population &amp; Area &amp; HDI \\\midrule France &amp; $66 \cdot 10^6$ &amp; $668763\text{km}^2$ &amp; 0.89 \\ Germany &amp; $81 \cdot 10^6$ &amp; $357167\text{km}^2$ &amp; 0.92 \\ United States &amp; $317 \cdot 10^6$ &amp; $9629091\text{km}^2$ &amp; 0.94 \\ \bottomrule \end{tabular} \caption{Information about countries} \label{table:countries} \end{table} Aenean sit amet felis eu urna accumsan consectetur. Sed hendrerit ultrices turpis nec fringilla. Pellentesque sagittis neque placerat, pharetra ante quis, maximus eros. Nam ultrices lacinia magna, eget interdum tortor ornare ut. Praesent semper tristique consectetur. Sed auctor, orci accumsan imperdiet vestibulum, nunc augue sagittis purus, sed dapibus neque arcu sit amet enim. Aliquam fermentum dui eu efficitur condimentum. Maecenas viverra metus ut bibendum pellentesque. Integer non interdum massa. Vestibulum non enim vulputate, sodales nunc ac, ultricies tortor. Suspendisse non vehicula ipsum, quis consequat elit. Quisque rutrum tincidunt lorem id semper. Phasellus bibendum nulla sit amet purus tempus, vitae tincidunt ligula ornare. Nunc quis felis non ex consequat elementum nec sit amet magna. In lacinia nulla nec neque venenatis, vel tristique risus blandit. \end{document} </pre></div> </div> </div> <p>which looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/09/latex-table-booktabs.png"><img src="//martin-thoma.com/captions/latex-table-booktabs.png" alt="LaTeX table with booktabs" width="500" height="232" class="" /></a><p class="wp-caption-text">LaTeX table with booktabs</p></div> <h3 id="combining-cells">Combining cells</h3> <p>It is much nicer when you combine cells. To do so, you can use <code>\multicolumn</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper]{scrartcl} \usepackage{amssymb, amsmath} % needed for math \usepackage{booktabs} % for \toprule, \midrule and \bottomrule \begin{document} Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis malesuada efficitur volutpat. Proin eget dui in lacus fermentum pharetra. Sed ut facilisis leo, sed consectetur urna. Phasellus eget tempus eros, vitae sagittis mi. Nullam pharetra, dolor a efficitur blandit, nisl velit interdum turpis, vel posuere lorem justo nec elit. Donec mattis massa auctor mattis varius. Nunc sed volutpat sapien, at finibus lectus. Phasellus auctor vehicula auctor. Nam vitae purus ut orci accumsan auctor. Fusce volutpat, tortor consectetur convallis aliquam, enim velit gravida sapien, id convallis nisi nunc ac leo. \begin{table}[ht] \centering \begin{tabular}{llll} \toprule Country &amp; \multicolumn{3}{c}{Property}\\ \cmidrule{2-4} &amp; {Population} &amp; {Area} &amp; {HDI} \\ &amp; {(mio.)} &amp; {(km\textsuperscript{2})}\\ \midrule France &amp; \multirow{2}{c}{66} &amp; 668763 &amp; 0.89 \\ Germany &amp; 81 &amp; 357167 &amp; 0.92 \\ United States &amp; 317 &amp; 9629091 &amp; 0.94 \\ \bottomrule \end{tabular} \caption{Information about countries} \label{table:countries} \end{table} Aenean sit amet felis eu urna accumsan consectetur. Sed hendrerit ultrices turpis nec fringilla. Pellentesque sagittis neque placerat, pharetra ante quis, maximus eros. Nam ultrices lacinia magna, eget interdum tortor ornare ut. Praesent semper tristique consectetur. Sed auctor, orci accumsan imperdiet vestibulum, nunc augue sagittis purus, sed dapibus neque arcu sit amet enim. Aliquam fermentum dui eu efficitur condimentum. Maecenas viverra metus ut bibendum pellentesque. Integer non interdum massa. Vestibulum non enim vulputate, sodales nunc ac, ultricies tortor. Suspendisse non vehicula ipsum, quis consequat elit. Quisque rutrum tincidunt lorem id semper. Phasellus bibendum nulla sit amet purus tempus, vitae tincidunt ligula ornare. Nunc quis felis non ex consequat elementum nec sit amet magna. In lacinia nulla nec neque venenatis, vel tristique risus blandit. \end{document} </pre></div> </div> </div> <p>which looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/09/latex-multicols.png"><img src="//martin-thoma.com/captions/latex-multicols.png" alt="LaTeX table with multicols" width="500" height="271" class="" /></a><p class="wp-caption-text">LaTeX table with multicols</p></div> <p>Note the <code>\cmidrule{2-4}</code> which draws a rule from cell 2 to 4 (LaTeX starts to count at 1).</p> <p>If you want to combine multiple rows you need to use <code>\usepackage{multirow}</code>.</p> <h3 id="page-breaking-tables">Page breaking tables</h3> <p>If you want your tables to be able to break over pages, you have to use <a href="ftp://ftp.tex.ac.uk/tex-archive/macros/latex/required/tools/longtable.pdf"><code>\usepackage{longtable}</code></a> which has <a href="http://users.sdsc.edu/~ssmallen/latex/longtable.html">an example</a>.</p> <p>Another option is <a href="http://ctan.org/pkg/supertabular">supertabular</a>.</p> <p>When you use them, you should add <code>\endhead</code> so that the head can get repeated.</p> <h2 id="tools">Tools</h2> <p><a href="http://truben.no/table/">truben.no/table</a> is an awesome page to create tables for different formats.</p> <h2 id="what-could-be-better">What could be better</h2> <p><strong>Page-breaking</strong>: I understand that you don’t want to have page breaking of tables most of the time. But rather than never allowing page-breaking, I would expect an optimization with the following thoughts in mind:</p> <ul> <li>It is best to have the table where it was specified.</li> <li>The content should have at least 2 times as many rows as the header. So when there is only one header row, there should be at least 2 content rows.</li> <li>The farer a table is away from its “original” position, the worse it is.</li> </ul> <p><strong>Headers</strong>: A semantic way to define the header and a tail would be very good. <code>\endhead</code> is ok.</p> <p><strong>Semantics, Styles and Classes</strong>: LaTeX hides some of the formatting for semantic codes. For example, you write <code>\section{MySection}</code> instead of <code>{\fontsize{12}{15}\textbf{MySection}}</code> or something similar. That should be more often the case. In fact, I think it would be very nice if LaTeX had some built-in support for pure stylesheets (like CSS for HTML). It would be very nice if I only had to define that I want to make a standard table and it inserts <code>\toprule</code>, <code>\midrule</code> and <code>\bottomrule</code> automatically. But to get an automatic <code>\midrule</code> we need a command to tell LaTeX where the header ends.</p> <p>Everything of the above should be standard. There should not be the need to use new packages for that. Also, <code>\multirow</code>, <code>\toprule</code>, <code>\midrule</code>, <code>\bottomrule</code> should not be “hidden” in a package but be there by default.</p> <p><strong>Table seperator</strong>: It is unfortunate that the table cell seperator(s) <code>\\</code> and <code>&amp;</code> have problems with matrices. I think one environment should get closed before the other one can continue parsing, so I don’t quite understand where the problem is. But there certainly is a problem (see <a href="http://stackoverflow.com/q/25971178/562769">this question</a>).</p> <p><strong>Tools</strong>: I don’t know any tools that can export LaTeX tables and merge cells. Such tools should be able to import and export LaTeX tables</p> <h2 id="see-also">See also</h2> <ul> <li><a href="https://www.tug.org/TUGboat/tb28-3/tb90hoeppner.pdf">Typesetting tables with LaTeX</a></li> <li><a href="https://en.wikibooks.org/wiki/LaTeX/Tables">LaTeX/Tables</a></li> </ul> Hörspiele //martin-thoma.com/horspiele/ Tue, 30 Dec 2014 21:51:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/horspiele <div class="info">This is a quic article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>Ich habe früher (damals, als ich noch keinen PC hatte ☺ ) sehr gerne Hörspiele gehört. Nun, mit meinem neuen Smartphone, dachte ich könnte ich das ja mal wieder machen.</p> <p>Auf der Suche nach (kostenlosen) Hörspielen habe ich folgendes gefunden:</p> <ul> <li><a href="http://neuvertonung.de/">Neuvertonung.de</a>: Eine kleine Gruppe hat „Die drei ???“ neu vertont. Eine Liste der Folgen gibts <a href="http://fragezeichen.neuvertonung.de/folgen.php?Details=on">hier</a>.</li> <li>YouTube <ul> <li><a href="https://www.youtube.com/watch?v=3JrW71xO58g&amp;index=13&amp;list=WL">Der Hexenmeister - Atmosphärisches Hörbuch / Hörspiel</a></li> <li><a href="https://www.youtube.com/watch?v=5EJ3y13qOV8&amp;index=17&amp;list=WL">Die Barash-Tyr Chroniken</a></li> <li><a href="https://www.youtube.com/watch?v=B0gdM_gYBNo&amp;list=WL&amp;index=25">Meuterei auf der Bounty</a></li> </ul> </li> </ul> Trickreiche Matheaufgaben //martin-thoma.com/trickreiche-matheaufgaben/ Tue, 30 Dec 2014 21:30:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/trickreiche-matheaufgaben <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>Ich finde immer wieder ein paar einfache, aber irgendwie trickreiche Matheaufgaben. Was genau ich damit meine, seht ihr am besten am folgendem Beispiel.</p> <h2>Wechselgeld</h2> <h3>Aufgabe</h3> <blockquote>Drei Kinder haben je 10 Euro und kaufen sich dafür gemeinsam einen Ball für 30 Euro. Nach dem Verkauf stellt der Ladeninhaber fest, dass der Ball nur 25 Euro kostet und schickt seinen Lehrling mit den überzähligen 5 Euro den Kindern nach. Der Lehrling gibt jedem Kind 1 Euro und behält für seine Bemühungen die restlichen 2 Euro. Damit hat jedes Kind nur 9 Euro für den Ball bezahlt, insgesamt zahlten die Kinder 27 Euro. Mit den 2 Euro des Lehrlings ergibt das aber erst 29 Euro.</blockquote> <p>Quelle: <a href="http://dsm-faq.wikidot.com/denksport">dsm-faq.wikidot.com/denksport</a></p> <h3>Auflösung</h3> <p>Das Problem dieser Aufgabe ist, dass man sich nicht klar macht, wo man hin will. Man will scheinbar herausfinden, wo das Geld geblieben ist. Das vermischt man aber mit dem Geld, das man hatte:</p> <p>Situation vor dem Kauf:</p> <ul> <li>Kinder: je 10 Euro</li> <li>Lehrling: 0 Euro</li> <li>Ladeninhaber: 0 Euro</li> Situation nach der Geschichte: <ul> <li>3 Kinder: je 1 Euro</li> <li>Lehrling: 2 Euro</li> <li>Ladeninhaber: 25 Euro</li> </ul> Der Lehrling ist also derjenige, der das Problem trickreich macht, wenn man nicht aufpasst. Er bestiehlt die Kinder, deshalb zahlen sie praktisch 27 Euro anstelle der 25 Euro und von diesen 27 Euro hat der Ladeninhaber 25 Euro. <h2>Mücke und Elefant</h2> <h3>Aufgabenstellung</h3> <blockquote>Sei `$x$` das Gewicht des Elefanten und `$y$` das Gewicht der Mücke. Sei `$d$` der Unterschied.<br /> `$\begin{align} x &amp;= y + d | \cdot (x-y)\\ x^2 - xy &amp;= xy + xd - y^2 - yd | -xd \\ x^2 - xy - xd &amp;= xy - y^2 - yd\\ x(x-y-d) &amp;= y \cdot (x-y-d) |:(x-y-d)\\ x &amp;=y \end{align}$` Das Gewicht der Mücke ist also gleich dem Gewicht des Elefanten!</blockquote> Quelle: <a href="http://dsm-faq.wikidot.com/denksport">dsm-faq.wikidot.com/denksport</a> <h3>Auflösung</h3> Es empfiehlt sich, wie immer bei Umformungen, sich klar zu machen durch was man teilt. Es gilt: `$(x-y-d) = 0$`, es wurde also durch 0 geteilt. Dabei passieren schlimme Dinge. Unter anderem kann man aus einer Mücke einen Elefanten machen ;-) <h2>Jeder Mensch hat sein Idealgewicht</h2> <h3>Aufgabenstellung</h3> Sei `$x$` das Körpergewicht in kg eines Menschen, `$y$` sein Idealgewicht und `$u$` das Übergewicht. Bei Untergewicht kann u also auch negativ sein! Dann gilt offensichtlich: `$x = y + u$` Nun kann man umformen: `$\begin{align} x &amp;= y + u | \cdot (x - y)\\ \Leftrightarrow x^2 - xy &amp;= xy + xu - y^2 - uy | -xu\\ \Leftrightarrow x^2 - xy - xu &amp;= xy - y^2 - uy\\ \Leftrightarrow x \cdot (x - y - u) &amp;= y \cdot (x - y - u) | : (x-y-u)\\ \Leftrightarrow x &amp;= y \end{align}$` Jeder Mensch hat also sein Idealgewicht! <h3>Auflösung</h3> Das Problem der Umformung ist das Gleiche wie oben: `$(x-y-u) = 0$`. </ul> Vertex coloring //martin-thoma.com/vertex-coloring/ Tue, 30 Dec 2014 21:29:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/vertex-coloring <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <h2>The problem</h2> <p>The <span style="font-variant: small-caps;">Vertex Coloring</span> problem can be described like this:</p> <div class="definition"> <span style="font-variant: small-caps;">Vertex Coloring</span> Let `$G = (V, E)$` be an undirected graph. Find a function `$f: V \rightarrow \{1, \dots, n\}, n \in \mathbb{N}$` such that: `$\forall e=\{v_1, v_2\} \in E: f(v_1) \neq f(v_2)$`. Minimize `$n$`. </div> <p>If <code>$n$</code> is minimal for <code>$G$</code>, it is called the chromatic number <code>$\chi(G)$</code>.</p> <p>What does that mean?</p> <p>You have a graph. Then you take pencils and color the vertices such all vertices that are connected are not of the same color.</p> <h2>Example</h2> <p>All of the following graphs show valid thee colorings:</p> <p>[caption id=”attachment_69831” align=”aligncenter” width=”500”]<a href="../images/2013/06/graph-with-three-colorings.png"><img src="../images/2013/06/graph-with-three-colorings.png" alt="Valid thee colorings of one graph" width="500" height="429" class="size-full wp-image-69831" /></a> Valid thee colorings of one graph<br />Source: <a href="http://commons.wikimedia.org/wiki/File:Graph_with_all_three-colourings_2.svg">Wikipedia</a>[/caption]</p> <h2>Interesting facts</h2> <ul> <li>`$1 \leq \chi(G) \leq |V|$`: You need at least one color and you could color all vertices with a different color</li> <li>`$\chi(K_n) = n$`: All <abbr title="all vertices are connected with all other vertices.">complete graphs</abbr> with `$n$` vertices need exactly `$n$` colors. One color for each vertex.</li> <li>Every planar graph can be colored with 4 colors (see <a href="http://en.wikipedia.org/wiki/Four_color_theorem">four color theorem</a>).</li> <li>Determining if a graph can be colored with 2 colors is equivalent to determining whether or not the graph is bipartite. This can be checked in polynomial time. You simply start with one vertex, give it color 1 and all adjacent vertices color 2. Then all adjacent vertices of color 2 have to have color 1, ...</li> <li><span style="font-variant: small-caps;">Vertex Coloring</span> is in `$\mathcal{NPC}$`.</li> <li>All triangle-free planar graphs can be 3-colored. You can get this coloring in linear time (<a href="http://en.wikipedia.org/wiki/Gr%C3%B6tzsch's_theorem#Computational_complexity">source</a>).</li> </ul> <h2>Algorithms</h2> <p>I think learning from errors is important. This is the reason why I share the following algorithm that do not work.</p> <h3>First WRONG try: Fix adjacent vertices</h3> <p>[caption id=”attachment_69891” align=”aligncenter” width=”512”]<a href="../images/2013/06/Vertex-coloring.png"><img src="../images/2013/06/Vertex-coloring.png" alt="A vertex coloring algorithm that does not work" width="512" height="281" class="size-full wp-image-69891" /></a> A vertex coloring algorithm that does not work[/caption]</p> <p>The time complexity of this algorithm is in <code>$\mathcal{O}(|V|^2)$</code>. This should make you suspicious, as <span style="font-variant: small-caps;">Vertex Coloring</span> is in <code>$\mathcal{NPC}$</code>. So if it was correct, it would solve the <a href="http://en.wikipedia.org/wiki/P_versus_NP_problem">P vs. NP problem</a> which is worth a million dollars.</p> <p>But an example why it doesn’t work is better. Just try it for the following graph:</p> <p>[caption id=”attachment_69921” align=”aligncenter” width=”512”]<a href="../images/2013/06/graph-v6-e8.png"><img src="../images/2013/06/graph-v6-e8.png" alt="Example that does not work with the provided algorithm" width="512" height="368" class="size-full wp-image-69921" /></a> Example that does not work with the provided algorithm[/caption]</p> <h3>Second WRONG try: Fix current vertex</h3> <p>[caption id=”attachment_69971” align=”aligncenter” width=”512”]<a href="../images/2013/06/Vertex-coloring-wrong-algorithm-2.png"><img src="../images/2013/06/Vertex-coloring-wrong-algorithm-2.png" alt="Another vertex coloring algorithm" width="512" height="315" class="size-full wp-image-69971" /></a> Another vertex coloring algorithm[/caption]</p> <p>This algorithm gives a valid coloring, but the coloring is not minimal.</p> <p>Example:</p> <p>When you apply the algorithm the the graph below, you will get a coloring with four colors. But obviously, it is possible to color it with three colors. [caption id=”attachment_69951” align=”aligncenter” width=”512”]<a href="../images/2013/06/graph-v6-e81.png"><img src="../images/2013/06/graph-v6-e81.png" alt="Graph that can be vertex-colored with 3 colors" width="512" height="368" class="size-full wp-image-69951" /></a> Graph that can be vertex-colored with 3 colors[/caption]</p> <h3>Brute force</h3> <p>It’s always a good idea to think about brute force algorithms. On the one hand, they are simple. So you can intuitively understand why they are correct and see their time / space complexity. On the other hand, you can use them for sanity checks of better algorithms for small problem instances.</p> <p>Here is a brute force algorithm for the vertex coloring problem [caption id=”attachment_70001” align=”aligncenter” width=”512”]<a href="../images/2013/06/Vertex-coloring-brute-force.png"><img src="../images/2013/06/Vertex-coloring-brute-force.png" alt="Brute force a minimal vertex coloring" width="512" height="333" class="size-full wp-image-70001" /></a> Brute force a minimal vertex coloring[/caption]</p> <p>You need <code>$\sum_{i=2}^n i^n$</code> steps at maximum. Wow. This is MUCH. Even when you only want to check if <code>$i$</code> colors are enough, you need <code>$i^n$</code>.</p> <p>You could use the second algorithm to get a better upper bound and try the next smaller ones. As soon as you don’t get valid colorings, you know that the number of colors you’ve used in the last valid coloring was the minimum number.</p> <h2>Zero-knowledge protocol</h2> <p>Vertex coloring is relevant for so called “zero-knowledge protocols”. This is a method by which one party (the prover) can prove to another party (the verifier) that a given statement is true, without conveying any additional information apart from the fact that the statement is indeed true.</p> <blockquote>A zero-knowledge proof must satisfy three properties: <ul> <li><strong>Completeness</strong>: if the statement is true, the honest verifier (that is, one following the protocol properly) will be convinced of this fact by an honest prover.</li> <li><strong>Soundness</strong>: if the statement is false, no cheating prover can convince the honest verifier that it is true, except with some small probability.</li> <li><strong>Zero-knowledge</strong>: if the statement is true, no cheating verifier learns anything other than this fact. This is formalized by showing that every cheating verifier has some ''simulator'' that, given only the statement to be proven (and no access to the prover), can produce a transcript that "looks like" an interaction between the honest prover and the cheating verifier.</li> </ul> </blockquote> <p>Source: <a href="http://en.wikipedia.org/wiki/Zero-knowledge_proof#Definition">Wikipedia</a></p> <p>Another great example is the following:</p> <blockquote>Imagine your friend is color-blind. You have two billiard balls; one is red, one is green, but they are otherwise identical. To your friend they seem completely identical, and he is skeptical that they are actually distinguishable. You want to prove to him (I say "him" as most color-blind people are male) that they are in fact differently-colored. On the other hand, you do not want him to learn which is red and which is green. Here is the proof system. You give the two balls to your friend so that he is holding one in each hand. You can see the balls at this point, but you don't tell him which is which. Your friend then puts both hands behind his back. Next, he either switches the balls between his hands, or leaves them be, with probability 1/2 each. Finally, he brings them out from behind his back. You now have to "guess" whether or not he switched the balls. By looking at their colors, you can of course say with certainty whether or not he switched them. On the other hand, if they were the same color and hence indistinguishable, there is no way you could guess correctly with probability higher than `$\frac{1}{2}$`. If you and your friend repeat this "proof" `$t$` times (for large `$t$`), your friend should become convinced that the balls are indeed differently colored; otherwise, the probability that you would have succeeded at identifying all the switch/non-switches is at most `$2^{-t}$`. Furthermore, the proof is "zero-knowledge" because your friend never learns which ball is green and which is red; indeed, he gains no knowledge about how to distinguish the balls.</blockquote> <p>Source: <a href="http://mathoverflow.net/questions/22624/example-of-a-good-zero-knowledge-proof/22628#22628">mathoverflow.net</a></p> <p>Lets make this more concrete. Say you want to authenticate somebody. This person is identified as the “only” person who knows a three-coloring of a big graph. This makes him/her special. If you simply asked him “what’s the three coloring for your graph?” he would no longer be the only person who knows the three coloring.</p> <p>So you want to get sure that he knows a three coloring without getting it.</p> <h2>See also</h2> <ul> <li><a href="http://web.mit.edu/~ezyang/Public/graph/svg.html">Interactive zero knowledge 3-colorability demonstration</a></li> </ul> Warum ist Q abzählbar? //martin-thoma.com/warum-ist-q-abzaehlbar/ Tue, 30 Dec 2014 21:27:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/warum-ist-q-abzaehlbar <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <div class="definition">Eine Menge B heißt <strong>abzählbar</strong> `$: \Leftrightarrow \exists (a_n) \in B: B = \{a_1, a_2, a_3, ...\}$` `$\Leftrightarrow \exists f : \mathbb{N} \rightarrow B $` mit `$f$` surjektiv.</div> <p>Die natürlichen Zahlen sind abzählbar. <strong>Beh.:</strong> <code>$\mathbb{N}$</code> ist abzählbar. <strong>Bew.</strong>: direkt Sei <code>$f: \mathbb{N} \rightarrow \mathbb{N}$</code> definiert durch <code>$f(n) := n$</code>. <code>$f$</code> ist also die identität und damit bijektiv und insbesondere surjektiv <code>$\blacksquare$</code></p> <p>Die ganzen Zahlen sind abzählbar. <strong>Beh.:</strong> <code>$\mathbb{Z}$</code> ist abzählbar. <strong>Bew.</strong>: direkt Sei <code>$f: \mathbb{N} \rightarrow \mathbb{Z}$</code> definiert durch <code>$f(n) := \begin{cases} \frac{n-1}{2} &amp; \text{, falls n ungerade} \\ - \frac{n}{2} &amp; \text{, falls n gerade} \end{cases}$</code>. Also: <code>$\forall z \in \mathbb{Z}: \exists x \in \mathbb{N} : f(x) = z$</code> da: <code>$\forall x \in \mathbb{Z}: n = \begin{cases} - 2 \cdot x &amp; \text{, falls x negativ} \\ 2 \cdot x + 1 &amp; \text{, falls x positiv} \end{cases}$</code></p> <p>Es gibt also für jede ganze Zahl z eine natürliche Zahl n, die ich in <code>$f$</code> stecken kann um z zu erhalten <code>$\blacksquare$</code></p> <p><strong>Beh.:</strong> <code>$\mathbb{N} \times \mathbb{N}$</code> ist abzählbar. <strong>Bew.</strong>: direkt Sei <code>$f: \mathbb{N} \times \mathbb{N} \rightarrow \mathbb{N}$</code> rekursiv definiert durch <code>$f(1,1) := 1$</code> und <code>$f (m, n) := \begin{cases} f(m + 1, n - 1) + 1 &amp; \text{, falls } n \neq 1 \\ f(1, m - 1) &amp; \text{sonst} \end{cases}$</code> Diese Abbildung sieht wie folgt aus: [caption id=”attachment_20501” align=”aligncenter” width=”322” caption=”Abbildung, die N x N auf N abbildet”]<a href="../images/2012/03/countable-set-n-times-n.png"><img src="../images/2012/03/countable-set-n-times-n.png" alt="Function that transforms N times N to N" title="Function that transforms N times N to N" width="322" height="288" class="size-full wp-image-20501" /></a>[/caption]</p> <p>Ich finde es ist intuitiv klar, dass diese Funktion bijektiv ist. Hat jemand dafür einen sauberen Beweis?</p> <p>Also gibt es eine Umkehrfunktion (die auch bijektiv ist). Also ist <code>$\mathbb{N} \times \mathbb{N}$</code> abzählbar <code>$\blacksquare$</code></p> <p><strong>Beh.:</strong> <code>$\mathbb{Q}^+$</code> ist abzählbar. <strong>Bew.</strong>: über <code>$N \times N$</code> Jede Zahl <code>$x \in \mathbb{Q}^+$</code> kann mit zwei natürlichen Zahlen dargestellt werden: <code>$x = \frac{p}{q}$</code>. Also gibt es eine Funktion <code>$f: \mathbb{N} \times \mathbb{N} \rightarrow \mathbb{Q}$</code> mit <code>$f(m, n) := \frac{m}{n}$</code>. Diese Abbildung ist offensichtlich surjektiv. <code>$\blacksquare$</code></p> <h2>Material</h2> <p>Die LaTeX-Dateien für die Bilder sind in diesem <a href="//martin-thoma.com/wp-content/uploads/2012/03/countable-sets.zip">Archiv</a> zu finden.<!--TODO--></p> Why I prefer Linux over Windows //martin-thoma.com/why-i-prefer-linux-over-windows/ Tue, 30 Dec 2014 21:25:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/why-i-prefer-linux-over-windows <div class="info">This is a quick article I had for quite a while as a draft.It might not be finished or have other problems, but I still want to share it.</div> <p>Some friends wondered why I prefer Linux over Windows. As I am currently using only Linux, I can make some examples.</p> <p>Here is an open list, why I prefer Linux over Windows:</p> <h2 id="no-marketing-strategies">No marketing strategies</h2> <p>Windows 7 comes in may flavours: Windows 7 Home, Windows 7 Home Premium, Windows 7 Ultimate, Windows 7 Enterprise, Windows 7 Professional, … (see <a href="../microsoft-product-flavor-hell/">Microsoft product flavor hell</a>)</p> <p>I have to admit that the choice of Linux can be difficult, too. You can choose from different distributions like Ubuntu, Suse, Fedora, … (see <a href="http://distrowatch.com/dwres.php?resource=major">distrowatch.com</a>) and some distributions offer different <a href="http://en.wikipedia.org/wiki/Comparison_of_X_Window_System_desktop_environments">desktop environments</a> like GNOME and KDE. The important difference is that Linux flavors depend on your needs, but Windows flavors depend on your money.</p> <h2 id="user-friendly-system">User-friendly system</h2> <p>As a Ubuntu 10.04 LTS user, I think that Ubuntu is much more user friendly than Windows 7. You have much more control about your system than you have on Windows (see <a href="../why-are-microsoft-products-so-user-unfriendly/">Why are Microsoft products so User unfriendly?</a>)</p> <p>Here are some everyday examples:</p> <ul> <li>Chaning the sound volume on a Notebook: You will see an indicator in Ubuntu <a href="http://www.markshuttleworth.com/wp-content/uploads/2009/02/notify-osd-screenshot.png">like this</a>. On Windows, you have to guess or wait until your movie starts</li> <li>Taking a screenshot: In Ubuntu, you only have to press "Print Screen". On Windows, you have to know Snipping tool or install some additional software. Additionally, it seems not to be possible to get a the key "Print Screen" as a shortcut for taking screenshots (<a href="http://superuser.com/q/524357/64857">source</a>).</li> <li>Different workspaces, pinning a window to "always in foreground" is definitely missing in Windows.</li> <li><a href="../pdf-printing-on-windows-7/">PDF-Printers</a>: oh my god. This is really sad.</li> </ul> <h2 id="better-community">Better community</h2> <p>When I have questions for my system, I can ask them on <a href="http://askubuntu.com/users/10425/moose?tab=questions">askubuntu.com</a>, <a href="http://unix.stackexchange.com/users/4784/moose?tab=questions">unix.stackexchange.com</a> or on <a href="http://forum.ubuntuusers.de/">ubuntuusers.de</a>. I usually get friendly answers that help me to fix my problem within a few minutes.</p> <p>Where do I find answers to Windows questions? I have tried <a href="http://superuser.com/users/64857/moose?tab=questions">superuser.com</a>, but is there anything else?</p> <h2 id="repositories">Repositories</h2> <p>When I want to install <code>something</code> on my Ubuntu machine, I simply type:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install something </pre></div> </div> </div> <p>When I want to install something on Windows, I have to Google for it. When I find a tool which seems to fit, I have to find out if it is for free or if it’s only a trial version. Then I need to find a way to download it and make sure that it’s not malware.</p> <p>When I want to update all software I have on my linux machine, I type:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get update sudo apt-get upgrade </pre></div> </div> </div> <p>After this command, my system and every single piece of software I have installed is updated. The updates are automatically installed in the background. A restart might be necessary, but until the restart is done the old software is used.</p> <p>On Windows, I have to:</p> <ol> <li>Click on the start button</li> <li>Type "update" in the search bar</li> <li>Click on "Search for updates"</li> <li>Install all updates</li> </ol> <p>A restart might be required. But I can’t simply make the restart when I want to. No, on Windows you will get reminded. You can choose the delay (max. 4 hours) of the reminder, but you can’t disable it. And this is only an update for the operating system. You have to look for updates of your software by yourself. For every single piece of software! This is not so easy. How do you find a reliable source of Updates e.g. for Unreal Tournament 2004?</p> <h2 id="terminal">Terminal</h2> <p>You can do everything with terminal. When the system is slowing down, I press <kbd>Ctrl</kbd> + <kbd>Alt</kbd> + <kbd>F4</kbd>, log into the shell, call <code>top</code> and <code>kill</code> the process which slows my system down.</p> <p>And I really like <a href="//martin-thoma.com/working-terminal/">ZSH and Oh-My-ZSH</a>.</p> <h2 id="linux-is-gratis">Linux is gratis</h2> <p>You don’t have to pay for it. In comparison, Windows 7 costs now (31.12.2014) about 50 Euro on Amazon. Although it is already outdated.</p> <h2 id="simple-stuff">Simple stuff</h2> <p>There are some simple, little things which I like when I use Linux. I can’t name them all, but some that come to my mind are:</p> <h3 id="livecd">LiveCD</h3> <p>Isn’t it great to have the possibility to use the OS from a CD / DVD only? This gives you the possibility to check if your system runs (or to diagnose what’s going wrong) without chaning anything.</p> <h3 id="installation-setup">Installation setup</h3> <p>The installation setup is great. It detects at the beginning if everything is ok (disk space, internet connection, battery) and tells you in simple words what is wrong. To chose your time zone you are shown a very simple graphic and by now the default was always correct for me. It continues with keyboard detection. Although the default was always wrong for me by now, it has an awesome auto-detection tool. You simply have to type some letters and it returns your layout. Great!</p> <h2 id="reasons-to-stay-with-windows">Reasons to stay with Windows</h2> <p>Although I don’t like Windows 7 for many reasons, I can see some reasons to stay with Windows:</p> <ul> <li>Linux doesn’t support your hardware (see <a href="../check-computer-hardware-for-linux-compatibility/">Check Computer / Hardware for Linux-compatibility</a>)</li> <li>Linux doesn’t support your software AND no free alternative exists (e.g. Photoshop for professionals)</li> </ul> <h2 id="pseudo-reasons-for-linux">Pseudo reasons for Linux</h2> <p>A pseudo-reason is an argument which might be true, but is not important at all for the person who wrote it.</p> <h3 id="security">Security</h3> <p>I often hear that people like Linux because of higher security. I don’t think that this is a real reason, as I have never heared of any end user having switched because of security reasons. I also don’t think that there is a significant difference of the bare systems in security.</p> <h3 id="freedom-to-change-code">Freedom to change code</h3> <p>Some people argue, that you can change the code of Linux / OpenSource programs according to your needs. This is only an argument, if you have done it at least once.</p> <h2 id="pseudo-reasons-against-linux">Pseudo reasons against Linux</h2> <h3 id="linux-is-only-for-geeks">Linux is only for geeks</h3> <p>This is obviously not true. I know at least some non-geeks who are able to use it.</p> <h3 id="linux-supports-no-games">Linux supports NO games!</h3> <p>Not true either. Steam gives A LOT of high quality games to Linux and you also have the possibility to use wine.</p> <p>However, if you want a specific game that might be a different story.</p> Don't lose your stuff //martin-thoma.com/dont-lose-your-stuff/ Mon, 29 Dec 2014 21:07:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/dont-lose-your-stuff <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>It is very annoying when you buy something expensive and you lose it or it gets stolen. But there are some technical solutions to prevent that.</p> <h2 id="crowd-gps-tags">Crowd GPS Tags</h2> <p>Crowd GPS devices use Bluetooth and connect with Smartphones. Whenever another person has the App installed, he/she sends the location of all devices to a server. This means as long as anybody is near the GPS tag, you can hope to find your stuff again.</p> <h3 id="tile">Tile</h3> <p><a href="https://www.thetileapp.com">Tile</a> is such a crowd GPS device.</p> <p>There is no android app yet.</p> <h3 id="tintag">TinTag</h3> <p><a href="http://thetintag.com/">TinTag</a> is a 28mm × 39.2mm device. Its battery lasts for 4 months. It has an LED and a buzzer as well as bluetooth. The bluetooth connection lasts for 100m.</p> <p>It has a <a href="https://www.indiegogo.com/projects/tintag-the-first-rechargeable-item-tracker/x/7191655">indigogo campagain</a>. 10 Tintag devices and 1 base charger cost 105 US-Dollar.</p> <p>Tintag app works on Android phones (version 4.3 and 4.4) and iPhone. It doesn’t work yet on Windows Phones or Blackberry.</p> <h3 id="trackr-bravo">TrackR bravo</h3> <p><a href="https://www.indiegogo.com/projects/trackr-bravo-the-thinnest-item-tracking-device-ever/x/7191655">TrackR bravo</a> is just another tagging device.</p> <p>TrackR is compatible with Android 4.4 (see <a href="https://play.google.com/store/apps/details?id=com.phonehalo.itemtracker">App</a>) and iPhone 4s &amp; later, iPad 3rd Generation &amp; later. It works with Bluetooth 4.0. It uses a CR1616 coin cell battery.</p> <p>It is 31mm in diameter and 3.5mm height.</p> <p>It can detect bluetooth devices up to 30m.</p> <p>One TrackR costs 29 US-Dollar, 10 cost 99 US-Dollar.</p> <h3 id="sticknfind">StickNFind</h3> <p><a href="https://www.sticknfind.com/">StickNFind</a> is probably the smallest Crowd GPS tag. It was <a href="https://www.indiegogo.com/projects/sticknfind-bluetooth-powered-ultra-small-location-stickers/x/7191655">on indiegogo</a> and raised 931.870 US-Dollar.</p> <p>It works with Android and iOS, as long as you have Bluetooth 4.0.</p> <p><strong>Specs</strong></p> <ul> <li><strong>Technology</strong>: Bluetooth 4.0 (Bluetooth Low Energy)</li> <li><strong>Range</strong>: Approximate 30m with line of sight.</li> <li><strong>Battery</strong>: Lasts up-to 1 year based on 30 minutes per day average use.</li> <li><strong>Battery Type</strong>: CR2016 watch battery. Battery is replaceable</li> <li><strong>Cost</strong>: A 10 pack costs 200 US-Dollar.</li> <li><strong>Dimensions</strong> <ul> <li>Shape: Cylindric</li> <li>Diameter: 2.4cm diameter</li> <li>Thickness: 4mm</li> <li>Weight: 4.5g</li> </ul> </li> </ul> <h2 id="selectadna">SelectaDNA</h2> <p><a href="https://www.selectadna.co.uk/">SelectaDNA</a></p> <h2 id="bicycles">Bicycles</h2> <p>Bicycles sometimes have a number on the frame. In German, it is called <a href="https://de.wikipedia.org/wiki/Fahrradrahmennummer">Fahrradrahmennummer</a>. In Germany, you can sometimes go to the police and they will add such a number to your bike. In case it gets stolen and the police finds it, they can look at their records and give it back to you. Eventually. I’m not sure how good this works. But it doesn’t cost anything, so why not?</p> <p>Another way is uglification. One way to do this is using <a href="http://dominicwilcox.com/portfolio/anti-theft-carbike-device/">these stickers</a>.</p> <p>Another way is putting lots of reflecting stuff on it. That has the advantage of giving you extra security as drivers can see you more easily.</p> <h2 id="usb-sticks">USB-Sticks</h2> <p>I always add a <code>README.txt</code> to the USB stick with the following content:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>## German Dieser USB-Stick gehört Martin Thoma. Wenn er verloren wurde, wäre es toll, wenn Sie eine E-Mail an info@martin-thoma.de schreiben würden. -------------------------------------------------------------- ## English This USB stick belongs to Martin Thoma. If it was lost, please send an e-mail to info@martin-thoma.de. </pre></div> </div> </div> <h2 id="luggage">Luggage</h2> <p>I always leave a note in my luggage with the following content:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Martin Thoma Parkstr. 17 76131 Karlsruhe Tel.: XXXX E-Mail: info@martin-thoma.de </pre></div> </div> </div> <h2 id="house">House</h2> <p>Locks and <a href="https://en.wikipedia.org/wiki/Key_(lock)">keys</a>… but you can lose your keys or forget them inside.</p> <p>When you lose your keys, you have to replace all locks. That’s a problem with traditional keys. But I could imagine that a good <a href="https://en.wikipedia.org/wiki/Keycard_lock">keycard lock</a> does not have this flaw. You “simply” tell the system that a card was lost and replace the cheap card - not the expensive lock. The card should only contain a long number. If the number is one of the allowed numbers, one can enter. If not, the system locks for 2 seconds. That should effectively prevent brute force.</p> <h2 id="smart-phones">Smart Phones</h2> <p>Android device manager</p> Packaging with Python //martin-thoma.com/python-packaging/ Mon, 29 Dec 2014 21:05:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-packaging <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it. I wrote this when I did not know much about packaging.</div> <p>The following article is a wrap-up of the talk <a href="https://www.youtube.com/watch?v=MSs3QmHhvpE">Python Packages</a> from Daniel Hepper given at a German <a href="https://2013.de.pycon.org/schedule/sessions/15/">PyCon 2013</a>.</p> <p>distutils have very limited functionality. This is the reason why you should use setuptools. But ‘distribute’ is compatible to setuptools.</p> <p><a href="https://pypi.python.org/pypi">PyPi</a> is the Python Package Index. They distribute packages in form of “eggs”. You can install them with easy_install or with pip.</p> <p>virtualenv / virtualenvwrapper</p> <h2 id="package-management-tools">Package Management Tools</h2> <h3 id="distutils">Distutils</h3> <p>Distutils is part of the standard library. When you run</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>python setup.py install </pre></div> </div> </div> <p>then distutils is running.</p> <p>Major disadvantages of distutils are:</p> <ul> <li>No Meta-data: <ul> <li>no deinstallation</li> <li>no dependencies</li> </ul> </li> <li>No Package listing (so you can’t automatically search pypi)</li> </ul> <h3 id="setuptools">Setuptools</h3> <p>Setuptools are startet when you install a package with <code>easy_install</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>easy_install package </pre></div> </div> </div> <p>Setuptools are an extension for distutils. Setuptools offers dependency management. With setuptools, so called ‘egg files’ were introduced. Those files are comparable to jar files in Java.</p> <h3 id="distribute">Distribute</h3> <p>Distribute was a fork of setuptools that got merged back to setuptools. So don’t use distribute, but use setuptools.</p> <h2 id="installer">Installer</h2> <h3 id="pip">PIP</h3> <p>PIP is short for ‘PIP installs Python’. It can only install files from sources; so it does not support egg files.</p> <p>PIP commands are</p> <ul> <li>install</li> <li>uninstall</li> <li>freeze</li> <li>search</li> <li>bundle</li> <li>unzip</li> <li>zip</li> <li>wheel</li> <li>help</li> </ul> <h2 id="environments">Environments</h2> <p>It might be the case that you have to have a Django 1.4 and a Django 1.5 project. In that case, you need different environments.</p> <h3 id="virtualenv">Virtualenv</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pip freeze $ virtualenv my_env $ source my_env/bin/activate </pre></div> </div> </div> <h3 id="virtualenvwrapper">Virtualenvwrapper</h3> <h2 id="creating-packages">Creating packages</h2> <p>A project could have this structure:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ tree . ├── LICENSE ├── MANIFEST ├── pyconde2013news │   └── __init__.py ├── README └── setup.py </pre></div> </div> </div> <p>With this setup.py:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">distutils.core</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">setup</span> setup(name=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">pycon2013news</span><span style="color:#710">&quot;</span></span>, version=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">0.1</span><span style="color:#710">&quot;</span></span>, py_modules=[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">pycon2013news</span><span style="color:#710">&quot;</span></span>],) </pre></div> </div> </div> <p>This can directly be registered on PyPi:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>python setup.py register </pre></div> </div> </div> <p>But a problem of this code is that it does not show the dependencies. So you should rather use setuptools for your setup.py:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">setuptools</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">setup</span> setup(name=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">pycon2013news</span><span style="color:#710">&quot;</span></span>, version=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">0.1</span><span style="color:#710">&quot;</span></span>, py_modules=[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">pycon2013news</span><span style="color:#710">&quot;</span></span>], description=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Reads latest news headlines from the PyCon.DE 2013 website</span><span style="color:#710">&quot;</span></span>) author=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Daniel Hepper</span><span style="color:#710">&quot;</span></span>, author_email=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">daniel@butfriendly.com</span><span style="color:#710">&quot;</span></span>, url=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">https://github.com/dhepper/pyconde2013news</span><span style="color:#710">&quot;</span></span>, install_requires=[ <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">beautifulsoup4==4.3.2</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">requests==2.0.0</span><span style="color:#710">&quot;</span></span> ] </pre></div> </div> </div> <p>When you add <code>scripts</code> argument to setup, you can later execute those. Entry points are also interesting.</p> <h2 id="additional-information">Additional information</h2> <ul> <li>http://guide.python-distribute.org/contributing.html</li> </ul> Chatbots //martin-thoma.com/chatbots/ Mon, 29 Dec 2014 21:05:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/chatbots <p>The <a href="https://en.wikipedia.org/wiki/Turing_test">Turing test</a> is an experiment that was proposed by Alan Turing to test the ability of an artificial intelligence to emulate intelligent behaviour. It works like this:</p> <p>A human judge gets to talk over a chat client with either a human he doesn’t know or a chat robot. If the judge can distinguish the human from the chat robot, the chat robot isn’t intelligent.</p> <p>(There is a lot more to say about the Turing test. If you’re really interested, you should read the wikipedia article.)</p> <p>Let’s see how long it takes for me to say that I’m either talking to a very dumb person or to a computer for various chat robots</p> <h2 id="alice">A.L.I.C.E.</h2> <p>See <a href="http://alice.pandorabots.com/">alice.pandorabots.com</a>.</p> <blockquote> <p>judge: hi ALICE: Hi there! judge: How are you? ALICE: I am fine, thank you. judge: What are your hobbies? ALICE: I like robots, computers, and chatting online. judge: So we do ☺ ALICE: Really.. I’m glad you find this amusing. judge: What is 7+3? ALICE: Use a calculator! judge: What was my last question? ALICE: Is this a trick question? judge: No. ALICE: It seems like a trick to me. judge: Could you simply answer it? ALICE: Please rephrase your question, judge. judge: Bye ALICE: Bye bye.</p> </blockquote> <table> <thead> <tr> <th>Check</th> <th>Difficulty</th> <th>How the Chatbot performed</th> <th>Stars</th> </tr> </thead> <tbody> <tr> <td>Greetings</td> <td>Easy</td> <td>He greated just as I’ve expected it.</td> <td>5 / 5</td> </tr> <tr> <td>Smalltalk</td> <td>Average</td> <td>He did not keep the talk running and he always answer the same way to smilies.</td> <td>3 / 5</td> </tr> <tr> <td>Tasks</td> <td>Average</td> <td>He avoided the task. Which is ok.</td> <td>4 / 5</td> </tr> <tr> <td>Back reference</td> <td>Hard</td> <td>Asking for a trick question and for rephrasing might be a good way to get the human to give the context in one chat message. Very good!</td> <td>3 / 5</td> </tr> </tbody> </table> <h2 id="cleverbot">Cleverbot</h2> <p>See <a href="http://www.cleverbot.com/">cleverbot.com</a>.</p> <blockquote> <p>judge: hi. Cleverbot: How are you? judge: I’m fine. How are you? Cleverbot: Good. judge: What are your hobbies? Cleverbot: Talking to query bots, you? judge: Hehe, very good. I like reading and going to the cinema. Cleverbot: What books do you like? judge: The sword of truth, Lord of the rings, The Dresden files. Cleverbot: Ok… judge: What is 7+3? Cleverbot: What is what? judge: What is the capital of the U.S.? Cleverbot: I don’t know. judge: Do you know any city? Cleverbot: No. judge: Where do you live? Cleverbot: Western Massachusetts. judge: That’s the state. And in which city do you live? Cleverbot: I will not tell. judge: Ok. Can you tell me what my last question was? Cleverbot: How can I get you to trust me. judge: Bye. Cleverbot: Ok, bye.</p> </blockquote> <table> <thead> <tr> <th>Check</th> <th>Difficulty</th> <th>How the Chatbot performed</th> <th>Stars</th> </tr> </thead> <tbody> <tr> <td>Greetings</td> <td>Easy</td> <td>He didn’t greet at the beginning.</td> <td>2 / 5</td> </tr> <tr> <td>Smalltalk</td> <td>Average</td> <td>Quite ok.</td> <td>4 / 5</td> </tr> <tr> <td>Tasks</td> <td>Average</td> <td> </td> <td>2 / 5</td> </tr> <tr> <td>Back reference</td> <td>Hard</td> <td> </td> <td>1 / 5</td> </tr> </tbody> </table> <p>This one tried to lead the conversation. I think that might be a good way to emulate a human. Either don’t talk or keep talking all the time so that you (your chatbot) know the context.</p> Cronjobs //martin-thoma.com/cronjobs/ Mon, 29 Dec 2014 21:00:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cronjobs <p>Cron is a very usefull service in Linux systems that allows periodical execution of programs.</p> <h2 id="terms">Terms</h2> <p>The program that runs other programs periodically is called “<a href="https://en.wikipedia.org/wiki/Cron">cron</a>”. The configuration file, that tells cron which programs should be run periodically is called “crontab” and located in <code>/etc/crontab</code>. One line in that file is called “cronjob”. But “crontab” is also a command that lets you add cronjobs.</p> <h2 id="example">Example</h2> <p>The following entry in crontab means that <code>uamt.py</code> is executed every day at 3:30 am:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>30 3 * * * /home/mthoma/uamt.py </pre></div> </div> </div> <p>You can check if everything went fine with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>mthoma@i13srv30:~&gt; crontab -l # DO NOT EDIT THIS FILE - edit the master and reinstall. # (/tmp/crontab.DEZBGc installed on Sat Jan 4 14:35:03 2014) # (Cronie version 4.2) 30 3 * * * /home/mthoma/uamt.py </pre></div> </div> </div> <h2 id="resources">Resources</h2> <ul> <li><a href="http://www.cyberciti.biz/faq/how-do-i-add-jobs-to-cron-under-linux-or-unix-oses/">HowTo: Add Jobs To cron Under Linux or UNIX?</a></li> </ul> SVN am KIT //martin-thoma.com/svn-am-kit/ Mon, 29 Dec 2014 20:57:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/svn-am-kit <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>Jeder Student mit einem <a href="http://www.atis.uka.de/">ATIS-Account</a> kann <a href="http://www.atis.uka.de/1422.php">hier</a> einen SVN-Zugang beantragen. Ich werde nun kurz erklären, wie man ihn mit der Konsole benutzt.</p> <h2>Import</h2> <p>Syntax (<a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.import.html">Hilfe</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn import [PATH] URL </pre></div> </div> </div> <p>Beispiel:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn import -m &quot;Initial import of the BankAccountReader project.&quot; /home/swt-user/BankAccountReader https://svnserver.informatik.kit.edu/stud/svn/s_thoma/trunk/BankAccountReader </pre></div> </div> </div> <h2>Checkout</h2> <p>Syntax (<a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.checkout.html">Hilfe</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn checkout URL[@REV]... [PATH] </pre></div> </div> </div> <p>Beispiel:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn co https://svnserver.informatik.kit.edu/stud/svn/s_thoma/trunk --username s_thoma </pre></div> </div> </div> <h2>Copy, Move, Delete</h2> <p><strong>Copy</strong> (<a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.copy.html">Hilfe</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn copy SRC[@REV]... DST </pre></div> </div> </div> <p>Beispiel:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn copy mySoureFile.java folder/myDestFile.java </pre></div> </div> </div> <p><strong>Move</strong> (<a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.move.html">Hilfe</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn move SRC... DST </pre></div> </div> </div> <p><strong>Delete</strong> (<a href="http://svnbook.red-bean.com/en/1.7/svn.ref.svn.c.delete.html">Help</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn delete PATH... </pre></div> </div> </div> <p>Für delete gibt es einige synonyme Befehle:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn rm myFile.java </pre></div> </div> </div> <p>Anders als der standard Linux <a href="http://linux.die.net/man/1/rm">rm-Befehl</a> ist der von SVN rekursiv!</p> <h2>status</h2> <p>Syntax (<a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.status.html">Hilfe</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn status [PATH...] </pre></div> </div> </div> <p>Beispiel:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn status D src D src/Tests.in D src/Tests.out D src/banking D src/banking/Status.java D src/banking/AccountNumber.java D src/banking/Shell.java D src/banking/Terminal.java D src/svn-commit.tmp A + BankAccountReader D BankAccountReader/svn-commit.tmp</code></pre></div> <h2>commit</h2> <p>Syntax (<a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.commit.html">Hilfe</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn commit [PATH...] </pre></div> </div> </div> <p>Beispiel:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn commit -m <span class="s2">&quot;restructuring directory structure&quot;</span> Adding BankAccountReader Deleting BankAccountReader/svn-commit.tmp Deleting src Committed revision 3.</code></pre></div> <h2>Siehe auch</h2> <p><a href="http://svnbook.red-bean.com/en/1.6/svn.ref.html">Subversion complete reference</a></p> Subversion //martin-thoma.com/subversion/ Mon, 29 Dec 2014 20:57:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/subversion <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>Subversion or Apache Subversion or short svn is a is a software versioning and a revision control system. This allows you to step back to any point of the software and to develop simultaniously on the same project (but not on the same file). You have to make sure that no dependencies are broken, of course.</p> <p>Here is a little cheat sheet how to use SVN. I will demonstrate some on my Google Code OpenSource project <a href="https://code.google.com/p/community-chess/">Community Chess</a>.</p> <p>All commands are executed while I’m in my local working copy of the repository.</p> <h2>Get the repository</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn checkout https://community-chess.googlecode.com/svn/trunk/ community-chess --username themoosemind@googlemail.com </pre></div> </div> </div> <h2>Update to the latest version</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn update </pre></div> </div> </div> <h2>Check for changes</h2> <p>If you only want to check which files were modified, added or deleted you can execute</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn status </pre></div> </div> </div> <p>This will show your local changes.</p> <h2>File actions</h2> <p>The actions are simmilar to the console commands, but you have to add svn:</p> <h3>Copy</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn cp myFile.php copiedFile.php </pre></div> </div> </div> <h3>Delete</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn rm myFile.php </pre></div> </div> </div> <h3>Rename / Move</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn mv myFile.php folder/myNewFile.php </pre></div> </div> </div> <h3>Add file</h3> <p>If you created a file and want to submit it with the next commit, just do</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn add myFile.php </pre></div> </div> </div> <h2>Commit the latest changes</h2> <h3>Check your changes</h3> <p>First you should try <a href="#Check_for_changes-3">svn status</a>. What files did you change? Do you really want to upload those changes?</p> <p>If svn status gives you an exclamation mark (!), you might have deleted a file which you wanted to add before. No problem. Just make</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn rever /path/to/your/file.php </pre></div> </div> </div> <h3>I'm fine: Upload it!</h3> <p>This is the command you use, if you want to send the changes you made on your working copy to the repository:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn commit -m &quot;Moved some functions to additional.inc.php to keep the project more flexible; Much work for tournament implementation done; Some Warnings fixed&quot; --username themoosemind@gmail.com </pre></div> </div> </div> <h2>Watch changes</h2> <h3>General</h3> <p>See the last three changes:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn log -v --limit=3 </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>------------------------------------------------------------------------ r118 | themoosemind@gmail.com | 2011-09-26 23:18:42 +0200 (Mo, 26. Sep 2011) | 1 Zeile Geänderte Pfade: M /trunk/clients/Java/ChessClient.class M /trunk/clients/Java/ChessClient.java small changes on the Java Client ------------------------------------------------------------------------ r116 | themoosemind@gmail.com | 2011-09-26 22:53:01 +0200 (Mo, 26. Sep 2011) | 1 Zeile Geänderte Pfade: A /trunk/clients/Java A /trunk/clients/Java/ChessClient.class A /trunk/clients/Java/ChessClient.java A /trunk/install/phpBB3 A /trunk/install/phpBB3/login.wrapper.php (von /trunk/install/phpbb3.login.php:100) A /trunk/install/phpBB3/phpbb3.integration.txt (von /trunk/install/phpbb3.integration.txt:113) A /trunk/install/phpBB3/phpbb3.php (von /trunk/install/phpbb3.php:100) A /trunk/install/phpBB3/phpbb3.sql (von /trunk/install/phpbb3.sql:103) A /trunk/install/phpBB3/wrapper.inc.php (von /trunk/install/phpbb3.wrapper.inc.php:113) D /trunk/install/phpbb3.integration.txt D /trunk/install/phpbb3.login.php D /trunk/install/phpbb3.php D /trunk/install/phpbb3.sql D /trunk/install/phpbb3.wrapper.inc.php Made integration instructions for phpBB easier; added Java-Client ------------------------------------------------------------------------ r113 | themoosemind@gmail.com | 2011-09-26 08:29:15 +0200 (Mo, 26. Sep 2011) | 1 Zeile Geänderte Pfade: M /trunk/index.php M /trunk/install/chess.sql M /trunk/install/phpbb3.integration.txt M /trunk/install/phpbb3.wrapper.inc.php M /trunk/my_software.php M /trunk/wrapper.inc.php Fixed issue 3 and some more phpBB-Bugs; more detailed integration instructions;Renamed GAMES_THREEFOLD_REPETITION_TABLE ------------------------------------------------------------------------ </pre></div> </div> </div> <h3>One specific file</h3> <p>I don’t want to get that much output, so I don’t apply -v this time:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn log index.php --limit=3 </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>------------------------------------------------------------------------ r127 | themoosemind@gmail.com | 2011-10-04 00:09:59 +0200 (Di, 04. Okt 2011) | 1 Zeile Moved some functions to additional.inc.php to keep the project more flexible; Much work for tournament implementation done; Some Warnings fixed ------------------------------------------------------------------------ r113 | themoosemind@gmail.com | 2011-09-26 08:29:15 +0200 (Mo, 26. Sep 2011) | 1 Zeile Fixed issue 3 and some more phpBB-Bugs; more detailed integration instructions;Renamed GAMES_THREEFOLD_REPETITION_TABLE ------------------------------------------------------------------------ r71 | themoosemind@gmail.com | 2011-08-26 23:13:37 +0200 (Fr, 26. Aug 2011) | 1 Zeile completed MVC with Vemplator; controlled every php file with phpcs ------------------------------------------------------------------------ </pre></div> </div> </div> Scherzfragen //martin-thoma.com/scherzfragen/ Mon, 29 Dec 2014 20:56:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/scherzfragen <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>Um die Antworten der folgenden Scherzfrangen zu erhalten müsst ihr einfach den schwarzen Text markieren.</p> <h2>Tierkonferenz</h2> <p>Wie bekommt man den Elefanten in den Kühlschrank? <span style="background-color:#000;color:#000">Kühlschranktür auf, Elefant rein, Kühlschranktür zu.</span></p> <p>Wie bekommt man die Giraffe in den Kühlschrank? <span style="background-color:#000;color:#000">Kühlschranktür auf, Elefant raus, Giraffe rein, Kühlschranktür zu.</span></p> <p>Wichtige Tierkonferenz: Welches Tier fehlt? <span style="background-color:#000;color:#000">Die Giraffe, die ist noch im Kühlschrank.</span></p> <p>Du kommst im Urwald zu einem Fluss mit gefährlichen Krokodilen. Keine Brücke, kein Boot…nichts. Wie kommst du hinüber? <span style="background-color:#000;color:#000">Schwimmen - Die Krokodile sind auf der Konferenz.</span></p> <p>Wie merkt man, dass ein Elefant im Kühlschrank war? <span style="background-color:#000;color:#000">An den Fußstapfen in der Butter.</span></p> <p>Warum darf man nach 24 Uhr nicht mehr in den Urwald? <span style="background-color:#000;color:#000">Weil dann die elefanten Fallschirm springen.</span></p> <p>Warum haben Krokodile so platte Nasen? <span style="background-color:#000;color:#000">Weil sie nach 24 Uhr im Urwald waren.</span></p> <h2>Autokollision</h2> <p>Was sagt ein Hund kurz bevor er von einem Auto angefahren wird? <span style="background-color:#000;color:#000">hilf…</span></p> <p>Und ein Pferd? <span style="background-color:#000;color:#000">hilf… </span></p> <p>Und ein Elefant? <span style="background-color:#000;color:#000">Komm nur.</span></p> <h2>Busfahrer</h2> <p>Du bist der Busfahrer. Der Bus startet den Motor und fährt los. Es steigen fünf Leute ein. Er fährt weiter und drei steigen aus. Weiter geht es, und sieben steigen ein, und fünf aus. Der Bus hält und alle müssen aussteigen weil jetzt Endhaltestation ist.</p> <p>Frage: Wie alt ist der Busfahrer? <span style="background-color:#000;color:#000">DU bist der Busfahrer!</span></p> <h2>Schnell antworten</h2> <p>Was ist schwerer, ein Kilo Federn, oder ein Kilo Blei? <span style="background-color:#000;color:#000">Es ist beides gleichschwer, ein kg ist ein kg.</span></p> <p>Auf einer Stange sitzen 10 Tauben. Ein Jäger schießt eine Taube ab. Wie viele sitzen noch da? <span style="background-color:#000;color:#000">Es sitzt keine Taube mehr auf der Stange. Wenn eine erschossen wird fliegen die anderen weg.</span></p> <p>Du hast ein Streichholz und kommst in einen leeren kalten Raum, in dem du nichts weiter als eine Petroliumlampe, einen Kamin und einen Ölofen vorfindest. Was zündest du zuerst an? <span style="background-color:#000;color:#000">Bevor du irgendetwas anzünden kannst musst du zuerst das Streichholz anzünden.</span></p> <p>Welche Farbe hat Papier? <span style="background-color:#000;color:#000">Weiß.</span></p> <p>Welche Farbe hat die Heizung? <span style="background-color:#000;color:#000">Weiß.</span></p> <p>Welche Farbe hat die Wand? <span style="background-color:#000;color:#000">Weiß.</span></p> <p>Was trinken Kühe? <span style="background-color:#000;color:#000">Wasser.</span></p> <p>Ein Flugzeug stürzt auf der Grenze von Frankreich zu Deutschland ab. Wo werden die Überlebenden begraben? <span style="background-color:#000;color:#000">Überlebende werden nicht begraben.</span></p> <h2>Scherzfragen</h2> <p>Wie kann man Postbote ohne O schreiben? <span style="background-color:#000;color:#000">Briefträger.</span></p> <p>Was macht 999 mal “Tick” und einmal “Tack”? <span style="background-color:#000;color:#000">Ein Tausendfüßler mit einem Holzfuß.</span></p> <p>Was schwimmt und fängt mit B an? <span style="background-color:#000;color:#000">Brett.</span></p> <p>Was schwimmt und fängt mit N an? <span style="background-color:#000;color:#000">Noch ein Brett.</span></p> <p>Was schwimmt und fängt mit S an? <span style="background-color:#000;color:#000">Schon wieder ein Brett.</span></p> <p>Was ist braun, groß, lebt 10 Meter unter der Erde und frisst Steine? <span style="background-color:#000;color:#000">Der große, braune, unterirdische Steinfresser.</span></p> <p>Was ist braun, lebt 10 Meter unter der Erde und Frisst Sand? <span style="background-color:#000;color:#000">Die Oma vom großen, braunen, unterirdischen Steinfresser.</span></p> <p>Was sagt Tarzan wenn er ne Herde Elefanten durch den Wald laufen sieht? <span style="background-color:#000;color:#000">Guck mal, eine Herde Elefanten!</span> Was sagt Tarzan wenn er eine Herde Elefanten mit Sonnenbrille durch den Wald laufen sieht? <span style="background-color:#000;color:#000">Nichts, denn er erkennt sie nicht.</span> Was sagt Tarzan wenn er ne Herde Giraffen durch den Wald laufen sieht? <span style="background-color:#000;color:#000">Nochmal fall ich auf euer Verkleidungsspiel nicht rein!</span></p> <p>Wenn man ein Loch von Berlin aus quer durch die Erde bohren und einen Stein reinwerfen würde, wie weit würde er fallen? <span style="background-color:#000;color:#000">10 Meter, dann wird er vom großen, braunen unterirdischen Steinfresser aufgefressen.</span></p> <h2>Weitere</h2> <p>Wer reist ständig kostenlos um die Welt??? <span style="background-color:#000;color:#000">Der Mond.</span></p> Java Exceptions //martin-thoma.com/java-exceptions/ Mon, 29 Dec 2014 20:39:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-exceptions <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <h2>When to use Errors and Exceptions</h2> <blockquote>An Error is a subclass of Throwable that indicates serious problems that a reasonable application should not try to catch. Most such errors are abnormal conditions.</blockquote> <p>(Source: <a href="http://docs.oracle.com/javase/6/docs/api/java/lang/Error.html">Javadoc</a>)</p> <h2>How to throw an exception</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kt">void</span> <span class="nf">myMethod</span><span class="o">(</span> <span class="n">String</span> <span class="n">s</span> <span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(!</span><span class="n">isStringValid</span><span class="o">(</span><span class="n">s</span><span class="o">))</span> <span class="o">{</span> <span class="k">throw</span> <span class="k">new</span> <span class="nf">IllegalArgumentException</span><span class="o">(</span><span class="s">&quot;This string is not valid!&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Common Exceptions</h2> <ul> <li>IllegalArgumentException: One argument of the current method hasn’t the form it should have.</li> <li>IllegalStateException: The current object is in the wrong state.</li> <li>NullPointerException: A Null-Pointer was given, but it should have been an object.</li> </ul> <p>A long list of Exceptions is on <a href="http://wuhrr.wordpress.com/2007/11/22/java-exceptions-list/">Hai’s Blog</a>.</p> <h2>See also</h2> <ul> <li>http://docs.oracle.com/: <ul> <li><a href="http://docs.oracle.com/javase/1.4.2/docs/api/java/lang/Exception.html">Class Exception</a></li> </ul> </li> </ul> Famous Software Bugs //martin-thoma.com/famous-software-bugs/ Mon, 29 Dec 2014 20:32:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/famous-software-bugs <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <h2 id="mars-climate-oribiter">Mars Climate Oribiter</h2> <div style="width: 138px" class="wp-caption alignright"><a href="../images/2012/06/mars-climate-orbiter.jpg"><img src="../images/2012/06/mars-climate-orbiter.jpg" alt="Mars Climate Oribiter" width="" height="" class="size-full wp-image-28651 " /></a><p class="wp-caption-text">Mars Climate Oribiter</p></div> <p><strong>Type of Bug</strong>: Bad specification<br /> <strong>Description</strong>: The flight system software on the Mars Climate Orbiter was written to calculate thruster performance using the <em>metric unit</em> Newtons (N), while the ground crew was entering course correction and thruster data using the <em>Imperial measure</em> Pound-force (lbf).<br /> <strong>Outcome</strong>: The cost of the mission was <code>$327.6 million total for both orbiter and lander, $</code>193.1 million for spacecraft development, <code>$91.7 million for launching it, and $</code>42.8 million for mission operations.<br /> <strong>Source</strong>: <a href="http://en.wikipedia.org/wiki/Mars_Climate_Orbiter">Wikipedia</a></p> <h2 id="ariane-v88">Ariane V88</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/kYUrqdUyEpI" frameborder="0" allowfullscreen=""></iframe> <p>The <a href="http://de.wikipedia.org/wiki/Ariane_V88">Ariane V88</a> exploded 40 seconds after its start.</p> <p><strong>Type of Bug</strong>: The software was written for another type of hardware.<br /> <strong>Description</strong>: A 64 Bit floating point number was converted into a 16 bit integer in the “inertial reference system” → Overflow → the rocket got into a tilted position and destroyed itself for security reasons. The interesting part is, that this program wasn’t even needed for the flight! It had been developed for the Ariane 4.<br /> <strong>Outcome</strong>: 290 Million Euro destroyed</p> <h2 id="other">Other</h2> <ul> <li><a href="http://www.codinghorror.com/blog/2009/11/whitespace-the-silent-killer.html">Whitespace: The Silent Killer</a></li> <li><a href="http://bugsniffer.blogspot.de/2007/11/infamous-software-failures.html">History’s Most (In)Famous Software Failures</a></li> <li><a href="https://en.wikipedia.org/wiki/Mariner_1">Mariner 1</a></li> <li><a href="http://www.ual.es/~plopez/docencia/itis/patriot.htm">Roundoff Error and the Patriot Missile</a></li> </ul> <p>Do you know more?</p> Replicators //martin-thoma.com/replicators/ Mon, 29 Dec 2014 20:25:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/replicators <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>What would you need to explore space? There are some ideas in science fiction like <a href="https://en.wikipedia.org/wiki/Interstellar_ark">interstellar arks</a> and near lightspeed travel. But one concept might be easier to realize: Self-replicating, autonomous machines.</p> <h2 id="the-problem-of-interstellar-arks">The Problem of Interstellar Arks</h2> <p>Interstellar arks are space ships that are of enourmous size. They are big enough to have enough humans on it so that those humans can have childens over an limitles time without getting into trouble because of incest. <a href="http://www.sciencedirect.com/science/article/pii/S0006320707002534">Traill et al. [2007]</a> suggests that you need about 4000 individuals for a minimal viable population.</p> <p>Those 4000 people would need food, air, personal space. You would need resources to repair the ship and explore planets. Medicine. You would need fuel. That would be a lot of stuff.</p> <p>Bringing stuff from earth to space is expensive.</p> <p>And those people would eventually be trapped on that ship for many, many generations before they might find another habitable planet. You might eventually need to do <a href="https://en.wikipedia.org/wiki/Terraforming">terraforming</a>. I can’t even imagine the number of resources that would be needed for that.</p> <p>The next problem is that you would want the explorers to keep contact with earth. Those signals would either have to be highligh redundant (see <a href="https://en.wikipedia.org/wiki/Error_correcting_codes">error correcting codes</a>) or they might get received only partially. So eventually you would like to get relay stations that catch up the signal, correct errors (or request a new send of the broken part) and send it again.</p> <p>An ark would have to carry everything for that. That’s a problem because sending so much stuff from earth to space is expensive.</p> <h2 id="the-alternative-replicating-machines">The alternative: Replicating Machines</h2> <p>An alternative might be replicating machines. Machines don’t need personal space. They don’t need air. They don’t need food or medicine. They don’t run into psychical problems.</p> <p>But they do need energy. They need resources. And they either need to be really intelligent or they need to have clear instructions.</p> <p>I a working minimal space exploring construction kit (let’s call it MISECK, because that’s much shorter than ‘minimal space exploring construction set’) should be able to do the following:</p> <ul> <li><strong>Construct other MISECKs</strong> from resources that can be found in space (e.g. on asteroids, moons or planets). The plural was intended. Every MISECK would have to be able to produce at least two other MISECKs.</li> <li>Build <strong>communication satelites</strong>: That communication satelite would act as a relay station. It talks with other satelites, receives messages and sends messages. It is able to check if the received message has errors and request a new message in case of errors. They should also store as much information as possible. This way, one could eventually contact them and get information that might otherwise get lost.</li> <li>Build <strong>exploration satelites</strong> which can gather information about a planet. This information should be send to the communication satelites and finally back to earth.</li> <li>Build <strong>mining and construction robots</strong> that are able to mine all resources needed to construct MISECKS. That will include melting ore and constructing fabrics which are able to produce computer chips.</li> <li>Build <strong>power plants</strong>. Those might be solar cells, fusion/fission reactors or something completely different. But something has to provide the energy to make it possible to run all those machines and to travel enormous distances in space.</li> <li><strong>Explore and coordinate</strong>: This is a collaborative planning task. MISECKs have to know where other MISECKs are. If one MISECK gets destroyed by anything, there might still be something that is worth exploring.</li> </ul> <h2 id="see-also">See also</h2> <ul> <li>Wikipedia <ul> <li><a href="https://en.wikipedia.org/wiki/Interstellar_travel">Interstellar travel</a></li> <li><a href="https://en.wikipedia.org/wiki/Intergalactic_travel">Intergalactic travel</a></li> </ul> </li> <li>StackExchange <ul> <li><a href="http://biology.stackexchange.com/q/305/8014">Smallest viable reproducing population</a></li> </ul> </li> </ul> How to draw speech bubbles //martin-thoma.com/how-to-draw-speech-bubbles/ Mon, 29 Dec 2014 20:20:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-draw-speech-bubbles <div class="info">This is a quick article I had for quite a while as a draft. It might not be finished or have other problems, but I still want to share it.</div> <p>The nice icon is from <a href="https://commons.wikimedia.org/wiki/File:Crystal_Clear_app_personal.png">Wikipedia Commons</a> and part of the Crystal Clear project by Everaldo Coelho.</p> <h2 id="preparation">Preparation</h2> <ol> <li>Install <code>inkscape</code>.</li> <li>Get an image where you want to put the speech bubble.</li> <li>Add text with <kbd>F2</kbd></li> </ol> <p>Now it should looke like this:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2014/01/inkscape-speech-bubble-step-1.png"><img src="//martin-thoma.com/captions/inkscape-speech-bubble-step-1.png" alt="Speech bubbles" width="512" height="464" class="" /></a><p class="wp-caption-text">Preparation</p></div> <h2 id="rectangle">Rectangle</h2> <p>Now you have to put a rectangle (<kbd>F2</kbd>) or an ellipses (<kbd>F5</kbd>) around your text. The rectangle should be placed below the text (<kbd>Page down</kbd>).</p> <p>To make positioning easier, group the text and the surrounding box:</p> <ol> <li>Mark box by clicking on it</li> <li><kbd>Shift</kbd> + Click on the text</li> <li>Group with <kbd>Ctrl</kbd> + <kbd>G</kbd></li> </ol> <p>Now it should looke like this:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2014/01/inkscape-speech-bubble-step-2.png"><img src="//martin-thoma.com/captions/inkscape-speech-bubble-step-2.png" alt="Speech bubbles" width="512" height="464" class="" /></a><p class="wp-caption-text">Preparation</p></div> <h2 id="indicator">Indicator</h2> <p>To add the “indicator” that shows who spoke, press <kbd>Shift</kbd> + <kbd>F6</kbd> and add a triangle that overlaps with the box:</p> <div style="width: 325px" class="wp-caption aligncenter"><a href="../images/2014/01/inkscape-speech-bubble-step-3.png"><img src="../images/2014/01/inkscape-speech-bubble-step-3.png" alt="Speech bubbles" width="" height="" class="" /></a><p class="wp-caption-text">Preparation</p></div> <p>Then press <kbd>F2</kbd> to modify the path by nodes. Add some controll nodes in between by double-clicking on the path in between:</p> <div style="width: 325px" class="wp-caption aligncenter"><a href="../images/2014/01/inkscape-speech-bubble-step-4.png"><img src="../images/2014/01/inkscape-speech-bubble-step-4.png" alt="Speech bubbles" width="" height="" class="" /></a><p class="wp-caption-text">Preparation</p></div> <p>Then delete them. Now you have those round curves that can be manipulated with the little circles:</p> <div style="width: 325px" class="wp-caption aligncenter"><a href="../images/2014/01/inkscape-speech-bubble-step-5.png"><img src="../images/2014/01/inkscape-speech-bubble-step-5.png" alt="Speech bubbles" width="" height="" class="" /></a><p class="wp-caption-text">Preparation</p></div> Logo Design Tournament //martin-thoma.com/logo-design-tournament/ Mon, 29 Dec 2014 19:54:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/logo-design-tournament <p>The website logotournament.com offers a service for designers and owners of companies. You can define how much money you would like to spend for a new logo-set and how this logo should look like.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/12/logotournament.png"><img src="//martin-thoma.com/captions/logotournament.png" alt="Logo Tournament Website" width="500" height="326" class="" /></a><p class="wp-caption-text">Logo Tournament Website</p></div> <p>Just take a look at the contest brief of Move Ahead. I’ve made a screenshot of their Website. They use the typical Joomla-Icon. Their Logo isn’t very good.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/12/logo-tournament-move-ahead.png"><img src="//martin-thoma.com/captions/logo-tournament-move-ahead.png" alt="Proposed Logos on Logo Tournament" width="500" height="394" class="" /></a><p class="wp-caption-text">Proposed Logos on Logo Tournament</p></div> <p>Now take a look at the best submitted logos. Great, aren’t they? At the moment, 105 logos have been submitted for $375. The company can decide which ones they like and rank them. They pay only for one logo set, but they can choose from 105 logos.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/12/move-ahead-website-2011-03-07.png"><img src="//martin-thoma.com/captions/move-ahead-website-2011-03-07.png" alt="Move Ahead Website" width="500" height="354" class="" /></a><p class="wp-caption-text">Move Ahead Website</p></div> <p><em>Note</em>: This is a quick post from one of my old blogs.</p> How mathematics could change our future //martin-thoma.com/how-mathematics-could-change-our-future/ Fri, 26 Dec 2014 00:56:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-mathematics-could-change-our-future <p>Can you think of a solution for a problem that concerns the whole or most of humanity and could be solved for the next ten years or even forever with less than 1 million dollars?</p> <p>This was the title of a question I’ve recently found on Quora. I think this question is very interesting and I would like to share my thoughts about it.</p> <p>I think the answer is mathematics and computer science. Or lets rather say algorithms.</p> <p>There are multiple problems in mathematics and computer science which could have a severe impact on some areas which are important for the worlds economy. As we live in a globalized world, this will affect most of humanity. As algorithms don’t cost anything except for developing cost, it is certainly below 1 million dollars. In principle, everybody could come up with such algorithms.</p> <h2 id="p-vs-np">P vs NP</h2> <p>The <a href="https://en.wikipedia.org/wiki/P_versus_NP_problem">P versus NP problem</a> is one of the <a href="https://en.wikipedia.org/wiki/Millennium_Prize_Problems">Millennium Prize Problems</a>. Stated extremely simple, it asks whether every problem whose solution can be quickly verified by a computer can also be quickly solved by a computer. If somebody found an algorithm which solves one problem in the class NPC in fast, it will eventually boost many problems or allow us to solve problems which were not solvable before. Especially optimization problems.</p> <h2 id="optimization-problems">Optimization problems</h2> <p>There could be other algorithms which boost optimization problems, but do not help for the P vs. NP problem.</p> <p>Optimization is about allocating just the right amount of resources for a couple of goals to get the highest outcome.</p> <h2 id="fully-homomorphic-encryption">Fully homomorphic encryption</h2> <p>Finding efficient solutions for the problem that we don’t want cloud computing providers to know our data, but we want them to use their efficient data centers to run calculations on them. This would boost cloud computing and lead to a more efficient use of computational resources.</p> <h2 id="ai">A.I.</h2> <p>The development of a strong A.I. could lead to a technological singularity. This would be a boost for technology incomparable to anything before.</p> <p>However, even advancements in A.I. which are not strong A.I.s will help.</p> <p>They can lead to many new products where humans cannot cope with the data volume. One example would be medicine. IBM’s Watson is one first step to help doctors skip through the possible thousands of diagnoses and finding the most relevant and recent papers which could fit the problems of a patient. New diagnoses could be developed, the computer could help to create better (more accurate) tests for diseases. It could help to track the spread of diseases, predict it and thus help to contain it.</p> <h2 id="parallelization-and-compilers">Parallelization and Compilers</h2> <p>Developing a tool which automatically parallelizes sequential code could make all applications go faster. The same is true for advances in compiler technology. This could lead to less energy consumption and faster devices. As most people have contact to computers nowadays, this would affect everybody.</p> <p>Can you think of other areas where algorithms have a strong impact?</p> Shortfilms, Part III //martin-thoma.com/shortfilms-part-iii/ Thu, 11 Dec 2014 22:54:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/shortfilms-part-iii <div class="info">Here is the second part "<a href="../shortfilms-part-ii/">Shortfilms, Part II</a>".</div> <p>I’ve collected quite a few YouTube videos in my “watch later” list. Most of them were short movies which I wanted to share. Here you are!</p> <h2 id="azarkant">Azarkant</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/_zB_qSTAmCQ?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="the-raven">The Raven</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/ikJc456pi3g?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="the-archiver">The Archiver</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/XaQXNrEQKNU?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="hybrids">Hybrids</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/25-aYv47U5o?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="seed">SEED</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/VbDZmbx474k?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="rewind">REWIND</h2> <p>Not a short movie … but interesting nevertheless ☺</p> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/Vi6u14oGmh0?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="a-darwinian-future">A Darwinian Future</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/K1nvBf8U1aI?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="omega">OMEGA</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/3019nJDXVKs?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="paradox">Paradox</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/nnfh3qcpBxA?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="one-rat-short">One Rat Short</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/gZLllDTa3I8?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="the-chase">The Chase</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/0CfvnIAtK_0?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="devils-angels--dating">Devils, Angels &amp; Dating</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/rkddkbu-EMA?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="true-skin">True Skin</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/ETv3eNj46EM?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="the-silent-city">The Silent City</h2> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/cvY5aOcTihI?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="the-escape">The Escape</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/pES7YgRgf-Q?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="sam">Sam</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/fzrfrXhE-w4?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="giant-robot-vs-monster">Giant Robot vs Monster</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/EtiRzqKfv4g?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="witch">WITCH</h2> <p>ATTENTION: Very loud at the beginning!</p> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/-yfT-TdtKwc?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="rosa">Rosa</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/MG11zhX6_jo?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="natalis-teaser">Natalis Teaser</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/MUsj2fpPC4E?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="abe">ABE</h2> <p>Freaky … and scary (Psycho Horror)</p> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/NY_kVDiMkMs?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="spyfox">SpyFox</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/qjXVbmdSygo?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="when-you-kill-little-creatures-on-the-road-there-are-consequences">When you KILL Little Creatures on the road, there are consequences!</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/LsvlLtOqHVE?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="devil-claim">Devil Claim</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/noEpS9jiego?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="bear-n-wasteland">BEAR ‘N’ WASTELAND</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/tW8ZXbhZQgY?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="blik">BLIK</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/NnCqByTuUNw?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="legacy">LEGACY</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/IXRQsWB3PdE?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="tolerantia">TOLERANTIA</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/-b_6EvCKhAE?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="ark">ARK</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/0jVshYzZipc?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="copia">Copia</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/xtxfzSFeNG8?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="meet-buck">Meet Buck</h2> <iframe width="560" height="315" src="//www.youtube-nocookie.com/embed/dW7awX2q8FI?rel=0" frameborder="0" allowfullscreen=""></iframe> <h2 id="egghunt">Egghunt</h2> <iframe width="512" height="384" src="//www.youtube-nocookie.com/embed/52M5EfRkBBo?rel=0" frameborder="0" allowfullscreen=""></iframe> Play Audio //martin-thoma.com/play-audio/ Sun, 07 Dec 2014 00:31:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/play-audio <p>Our senses have a limited capability to distinguish signals. This might not be surpristing. However, we also have a limited capability to tell in which order signals arrived at our sensory organs.</p> <p>As I learned this, I wanted to check it. I wrote a little JavaScript / HTML5 page where you can check it. You can adjust the time in which two sounds are played. The clicking noise is played on the left and the right speaker in random order. A textfield below shows which speaker played the sound first.</p> <p>You should use headphones for this demo.</p> <p>According to the KIT lecture “Mensch-Maschine-Wechselwirkung in der Anthropomatik (Vorlesung Universität Karlsruhe im KIT, WS 2013/14, J. Geisler)”, the time resolution of the human ear is between 2 and 5 ms. This means you will not be able to distinguish the two signlas for less than 2ms. But you will need the signals to be 30-40ms apart to tell which one played first.</p> <p>I rather need 10ms, but this might also be caused by hardware problems. I doubt that JavaScripts <code>timeout</code> is accurate enough.</p> <h2>Audio Test</h2> <audio id="left_channel" src="//martin-thoma.com/audio/click_left.wav" preload="auto"></audio> <audio id="right_channel" src="//martin-thoma.com/audio/click_right.wav" preload="auto"></audio> <p><a href="javascript:play_sound();">Play sound</a> <input type="number" id="seconds" name="seconds" value="20" /> ms <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /> <br /></p> <h2>Which was first</h2> <p id="results"></p> <script type="text/javascript" src="//martin-thoma.com/js/playsounds.js"></script> The Impact of strong AIs //martin-thoma.com/the-impact-of-strong-ais/ Tue, 02 Dec 2014 15:18:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/the-impact-of-strong-ais <p>An artificial intelligence (AI) is a computer program which acts - according to its developers - intelligent. That could be anything. Typical examples are route finding algorithms, chess programs, ego shooter computer opponents and classifiers. The last category of AIs (classifiers) is huge and includes programs which try to find out what you were writing (see <a href="//martin-thoma.com/write-math/">my bachelor’s thesis</a>), try to figure out who is on an image (face recognition) or what was spoken (automatic speech recognition).</p> <h2 id="strong-and-weak-ais">Strong and Weak AIs</h2> <p>Science fiction literature distinguishes two kinds of AIs: Weak AIs and strong AIs.</p> <p>Currently, we only know weak AIs. They can do incredible things (see <a href="//martin-thoma.com/ai-in-computer-games/">A.I. in Computer Games</a> and <a href="//martin-thoma.com/awesome-robots/">Awesome Robots</a>), but that is nothing compared to a stong AI. Strong AIs are capable of adapting to completely new tasks. They can do creative work. In other words, they can do any task any human could do. They can do research and compose the most beautiful art. As they are machines which will be build by somebody (hence the term ‘artificial’), they are better understood than our biological brains. Strong AIs will be able to understand how they work themselfes and very likely be able to improve themselfes.</p> <p>This is the point where a <a href="https://en.wikipedia.org/wiki/Technological_singularity">technological singularity</a> happens. The machines start developing faster than any human can comprehend how they improve. At some point they will even develop faster than humankind together can understand.</p> <p>Now that you know the context, I would like to share an answer to the following question I’ve recently seen:</p> <h2 id="what-would-change-with-strong-ais">What would change with strong AIs?</h2> <p><strong>What happens when machines take all of our jobs including creative/research/artistic ones?</strong></p> <p>Something like that would not happen instantly. It is a gradual process. Many answers say something like nothing would be scarce. Well, I think that is wrong for two reasons:</p> <ul> <li><strong>Scarcity of resources</strong>: Oil, gold and diamonds are expensive. But they are not (only) expensive because it takes a high amount of work to get them, but also because the number of diamonds on earth is limited. More or cheaper “work hours” like much better AIs combined with much better robots would not solve that problem. Oh, and please don’t forget energy!</li> <li><strong>Distribution</strong>: I think we produce enough food so that nobody on earth would have to starve. We certainly have enough clean water for everybody. Why do so many people still starve and don’t have access to clean water? Because the distribution is not equal. Europe and the US make use of much more resources per person than Africa does. The richest 1% of the US make use of MUCH more resources than the bottom 30% (I guess the numbers are more extreme). Who do you think would own the robots that take the jobs? Who would profit from this much cheaper work hours? I think AIs that would in principle be able to solve any problem a human could solve (e.g. creating art and conducting research) would cause serious social problems if we don’t adapt to the new situation. Such AIs would have the potential for a much worse world than we currently live in.</li> </ul> <p>However, with the right politics, it could vastly improve our world. Having the insight how such AIs work, we could make them decide ultimatively unbiased for a greater good. They could be used to arbitrate a dispute as a neutral, intelligent instance. They could accelerate research. They could help us to understand ourselves.</p> <h2 id="job-market">Job market</h2> <p><strong>What is the effect of technological singularity in job market?</strong></p> <p>In a ideal world, everybody would only do the job he or she wants to do. We would eventually work less, but I think we would still work. Humans are resources and as such they will always be valuable in any economy.</p> <p>Another, darker, scenario is that AIs would gradually remove whole industries, starting with simple ones. Taxi and truck drivers are not necessary. They could step-by-step be replaced by AIs. However, no new jobs would be created for those people. They would have to get aid by the government. But as they would get less money, the economy would focus on the people who have money. That would be the people who own the AIs. At some point people would realize that they will never be able to get a new job. Even worse, their children will never be able to get a job. Extreme poverty would rise as the state gets less taxes (as less goods are consumed, because people have less money). The AIs would predict how every single person would most likely act. How could they do so? Well, you have a smartphone. Your conversations on WhatsApp, Twitter, Facebook, Gmail, … get tracked and automatically analyzed. You can be predicted to a certain degree. You can be influenced by personalized advertising. A really clever AI will make itself able to act in any possible scenario, replicate itself and make itself less dependent. In this dark scenario people would eventually start at some point to try to get more money from the people controlling the AIs, but how do you force them to do so? The police might also be replaced by AIs.</p> <p>My guess is that the reality would be somewhere in between. A couple of super-rich people and the rest giving them massages.</p> <h2 id="a-possible-solution-to-those-social-problems">A possible solution to those social problems</h2> <p>I’ve just described that AIs might cause serious social problems. However, I think we can solve those problems by making sure that income inequality cannot get too high. This means there should be very high and effective inheritance tax as well as a taxation system that prevents people from getting too rich / people too poor. The most extrem action to prevent too poor people is an unconditional income, the most extrem action to prevent people getting too rich is an upper limit on what somebody could have.</p> <p>I think an unconditional income would be a good thing, but its hard to tell how high that should be.</p> <p>The easiest way to prevent people from getting too rich is adding a tax system that adjusts to income:</p> <ul> <li>Your first 0 - 2000 Euro / month don’t get taxed at all</li> <li>Your next 2001 - 3000 Euro / month get taxed with 0% + (100%/2) = 50%</li> <li>Your next 3001 - 4000 Euro / month get taxed with 50% + (50%/2) = 75%</li> <li>Your next 4001 - 5000 Euro / month get taxed with 75% + (25%/2) = 87.5%</li> <li>…</li> </ul> <p>You can (and should - I think my numbers are not well-chosen!) argue about the exact numbers, but I guess you get what I mean. The tax should never be 100%, thus leaving the possibility to get more money. But the difficulty to do so should increase. This effectively prevents that some people get too rich and hence resulting in a very instable system.</p> <p>It would be important to do so before anybody develops a strong AI.</p> <h2 id="related-books-movies-and-talks">Related books, movies and talks</h2> <p><strong>Books</strong> (all fiction)</p> <ul> <li>“Zero” by Marc Elsberg: People get controlled by life improvement apps in a very indirect way.</li> <li>Out-Series by <a href="https://en.wikipedia.org/wiki/Andreas_Eschbach">Andreas Eschbach</a>: A device was developed, that lets people connect their brains. A new form of conciousness develops from that.</li> <li><a href="https://en.wikipedia.org/wiki/Brave_New_World">Brave new world</a> by <a href="https://en.wikipedia.org/wiki/Aldous_Huxley">Aldous Huxley</a>: People get distracted from issues by consuming many goods.</li> </ul> <p><strong>Movies</strong> (all fiction)</p> <ul> <li><a href="https://en.wikipedia.org/wiki/Transcendence_(2014_film)">Transcendence</a>: The mind of one person gets transformed in a computer.</li> <li><a href="https://en.wikipedia.org/wiki/I,_Robot">I, Robot</a>: An AI gets developed and very powerful humanoid robots get controlled by it.</li> </ul> <p><strong>Talks</strong></p> <ul> <li><a href="http://www.ted.com/talks/chrystia_freeland_the_rise_of_the_new_global_super_rich">The rise of the new global super-rich</a>: Technology is advancing in leaps and bounds — and so is economic inequality, says writer Chrystia Freeland. In an impassioned talk, she charts the rise of a new class of plutocrats (those who are extremely powerful because they are extremely wealthy), and suggests that globalization and new technology are actually fueling, rather than closing, the global income gap. Freeland lays out three problems with plutocracy … and one glimmer of hope.</li> </ul> <p>And a coulple of talks by people who are not active within AI / ML research themselves:</p> <ul> <li>Nick Bostrom: <a href="https://www.youtube.com/watch?v=pywF6ZzsghI">“Superintelligence”</a> - Strong AI is inevitable; we should set the initial conditions up the right way</li> <li><a href="https://www.youtube.com/watch?v=JybXEp7k7XU">Sam Harris and Joe Rogan talking about artificial intelligence</a></li> <li><a href="https://www.youtube.com/watch?v=W9N_Fsbngh8">Max Tegmark and Nick Bostrom speak to the UN about the threat of AI</a> <ul> <li><a href="https://en.wikipedia.org/wiki/United_Nations_Interregional_Crime_and_Justice_Research_Institute">UNICRI</a></li> </ul> </li> </ul> <p><strong>Articles</strong></p> <ul> <li><a href="http://uk.businessinsider.com/predictions-for-after-singularity-2015-11?IR=T">9 crazy things that could happen after the singularity, when robots become smarter than humans</a></li> </ul> Universal Rating System //martin-thoma.com/universal-rating-system/ Sat, 22 Nov 2014 17:19:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/universal-rating-system <p>A key feature of Amazon is its rating system. Rating systems are relatively straight-forward to build, but they need much data and get better with more data. I think Amazon builds a monopoly that way. However, I also think we could build an Universal Rating System (URS).</p> <p>Just as important as pure rating are reviews.</p> <h2 id="what-would-an-urs-need">What would an URS need?</h2> <p>Directly neccessary are</p> <ul> <li><strong>Identification of people</strong>: The same person should not be able to write multiple reviews or make multiple ratings for the same product. It is not important to tell which online-identity belongs to which person. In fact, I think it would be good if it was possible to keep users anonym while making sure that everybody has only one online-identity.</li> <li><strong>Identification of products</strong>: Users have to be able to find products and they have to find reviews to that product. So some kind of product identification number is necessary.</li> <li><strong>Ratings for reviews</strong></li> <li><strong>Uploading photographs</strong></li> <li><strong>Product description</strong>: This should be objective.</li> </ul> <p>Indirectly necessary are</p> <ul> <li><strong>Recommendations</strong>: If users see that they get good recommendations from an independant source they might use the system. If they see that those recommendations imporve with more reviews and more ratings, they add more of them. This way the system gets better.</li> <li><strong>Possibility to compare products</strong>: Examples are <a href="http://www.phonearena.com/">phonearena.com</a>, <a href="http://ark.intel.com/">ark.intel.com</a> and others. But they are always limited to some products.</li> <li><strong>Search</strong>: Users should be able to search for a product by specifying it. This could be a price range, a category, a review average, a minimum number of reviews, …</li> <li><strong>Easy login</strong>: Something like OpenID that makes it easy for users to create an account and sign in.</li> <li><em>*Right incentives</em>: Having a great community is much about giving the right incentives. Badages and Karma are a great way to do so as shown with StackExchange.</li> </ul> <p>Non-software parts</p> <ul> <li><strong>Advertisment</strong>: People have to get informed about such a system.</li> <li><strong>Organization</strong>: The software should be OpenSource, the data should be published (as far as possible without breaking privacy) and the organization which runs the software should be a nonprofit organization. The reason is simply that it prevents abuse.</li> <li><strong>Product registration</strong>: Companies should have the possibility to register their products to get an identification number.</li> <li><strong>Project name</strong>: A good name is important. Any ideas?</li> </ul> <h2 id="existing-projects">Existing Projects</h2> <p>Does anybody know if such a project already exists?</p> <p>If there is no such project by now: Is anybody interested in working on it?</p> Nyquist–Shannon sampling theorem //martin-thoma.com/nyquist-shannon-sampling-theorem/ Tue, 18 Nov 2014 17:41:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/nyquist-shannon-sampling-theorem <p>The <a href="https://en.wikipedia.org/wiki/Nyquist%E2%80%93Shannon_sampling_theorem">Nyquist–Shannon sampling theorem</a> states that you have to sample more than twice the highest frequency. If you sample less often, you will get aliasing.</p> <p>The following videos show what aliasing is:</p> <iframe width="512" height="384" src="//www.youtube-nocookie.com/embed/Fy9dJgGCWZI" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/A-19SxqZ8Qs" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="//www.youtube-nocookie.com/embed/tmzbFkzImQ4" frameborder="0" allowfullscreen=""></iframe> Formale Systeme Klausur //martin-thoma.com/formale-systeme/ Sun, 16 Nov 2014 17:05:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/formale-systeme <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Formale Systeme&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn Prof. Dr. Beckert im Wintersemester 2014/2015 gehört.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="folien">Folien</h3> <table> <tr> <th>Folien-<br />satz</th> <th>Inhalt</th> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/01Organisatorisches-print.pdf" rel="nofollow">01</a></td> <td>Organisatorisches</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/02ALIntro-print.pdf" rel="nofollow">02</a></td> <td>Aussagenlogik: Modellierung von Sudoku; 8-Damen-Problem; Allgemeine Syntax und Semantik sowie Grundbegriffe, Tautologien und Sätze; Basis; Erfüllbarkeit; Allgemeingültigkeit; \(M \models A\)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/03CraigInterpol-print.pdf" rel="nofollow">03</a></td> <td>Aussagenlogik: <a href="https://de.wikipedia.org/wiki/Craig-Interpolation">Craig-Interpolation</a></td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/04ALNormalform-print.pdf" rel="nofollow">04</a></td> <td>Aussagenlogik: Normalformen (<abbr title="Konjunktive Normalform">KNF</abbr>, <abbr title="Disjuktive Normalform">DNF</abbr>, <abbr title="Kurze konjunktive Normalform">KKNF</abbr>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/05BDD-print.pdf" rel="nofollow">05</a></td> <td>Binary Decision Diagrams: (normierte) Shannon-Formeln, sh-Operator, Shannon-Graph, Reduzierte Shannon-Graphen</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/06SATsolver-print.pdf" rel="nofollow">06</a></td> <td><a href="https://de.wikipedia.org/wiki/Erf%C3%BCllbarkeitsproblem_der_Aussagenlogik">SAT</a>; <a href="https://de.wikipedia.org/wiki/Satz_von_Cook">Satz von Cook</a>; <a href="https://de.wikipedia.org/wiki/Horn-Formel">Horn-Formeln</a>; <a href="https://de.wikipedia.org/wiki/Davis-Putnam-Verfahren">DPLL</a></td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/07PK1Intro-print.pdf" rel="nofollow">07</a></td> <td>Prädikatenlogik: Syntax (PL1); JML; (Kollisionsfreie) Substitutionen; <a href="https://de.wikipedia.org/wiki/Unifikation_(Logik)">Unifikation</a> und der Algorithmus von Robinson; Unifikationstheorem</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/08Pk1Semantik-print.pdf" rel="nofollow">08</a></td> <td>Pradikatenlogik: Semantik; Interpretation; Koinzidenzlemma; Substitutionslemma für Terme (und das für Formeln); Hoare-Kalkül; Modell; (Logische) Folgerung; Allgemeingültigkeit; Folgerbarkeit</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/09PK1Normalform-print.pdf" rel="nofollow">09</a></td> <td>Pradikatenlogik: Normalformen; Negationsnormalform; Pränexe Normalform; Skolem-Normalform; Herbrand-Strukturen; Satz von Herbrand; Endlichkeitssatz der Aussagenlogik</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/10IntroBeweistheorie-print.pdf" rel="nofollow">10</a></td> <td>Beweistheorie (Einführung)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/11Hilbert.pdf" rel="nofollow">11</a></td> <td>Hilbertkalkül; Deduktionstheorem; Vollständigkeit der PL1; Kompaktheitssatz; Endlichkeitssatz</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/12ALResolution-print.pdf" rel="nofollow">12</a></td> <td>Aussagenlogik: Resolutionskalkül; 1-Resolution</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/13PK1Resolution-print.pdf" rel="nofollow">13</a></td> <td>Prädikatenlogik: Resolutionskalkül</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/14Tableau-print.pdf" rel="nofollow">14</a></td> <td>Tableaukalkül</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/19PL1Sequenz-print.pdf" rel="nofollow">19</a></td> <td>Prädikatenlogik: Sequenzenkalkül</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/21Peano-print.pdf" rel="nofollow">21</a></td> <td>Peano-Arithmetik; Unentscheidbarkeit</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/28JML.pdf" rel="nofollow">28</a></td> <td>JML</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/22Reduktion-print.pdf" rel="nofollow">22</a></td> <td>Reduktionssysteme: Gleichungslogik; Satz von Birkhoff; Termersetzungssysteme; Reduktionssysteme; Kanonische Reduktionssysteme; Noethersche Induktion; (lokale) Konfluenz</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/23Termersetzung-print.pdf" rel="nofollow">23</a></td> <td>Termersetzungssysteme; Kritische Paare</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/27Modal-print.pdf" rel="nofollow">27</a></td> <td>Modallogik; Bakery-Algorithmus; Kripke-Strukturen; Charakterisierungstheorie; Entscheidbarkeit modaler Logiken</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/41Automaten-print.pdf" rel="nofollow">41</a></td> <td>(Vollständige) endliche Automaten; <abbr title="Nichtdeterministische Endliche Automaten">NEAs</abbr>; Spontane Übergänge; Satz von Myhill und Büchi (vgl. <a href="//martin-thoma.com/konstruktion-eines-deterministischen-endlichen-automaten-aus-einem-nicht-deterministischem/">Konstruktion</a>); Reguläre Ausdrücke</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/42buechiAut-print.pdf" rel="nofollow">42</a></td> <td>Büchi-Automaten; Zerlegungssatz</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/43LTL-print.pdf" rel="nofollow">43</a></td> <td>Lineare Temporale Logik; omega-Struktur; LTL-Formeln; LTL-Semantik; </td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/45LTL2Buechi-print.pdf" rel="nofollow">45</a></td> <td>LTL und Büchi-Automaten</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/50Wiederholung-print.pdf" rel="nonfollow">50</a></td> <td>Wiederholung</td> </tr> </table> <h3 id="bungsbltter">Übungsblätter</h3> <table> <tr> <th>Übungsblatt</th> <th>Lsg</th> <th>Inhalt</th> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt1.pdf" rel="nofollow">ÜB 1</a>: Aussagenlogik</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt1-lsg.pdf">Lsg</a></td> <td>Erfüllbarkeit, Unerfüllbarkeit, Allgemeingültigkeit, Tautologie, <abbr title="Konjunktive Normalform">KNF</abbr>, <abbr title="Disjuktive Normalform">DNF</abbr>, Interpolanten</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt2.pdf" rel="nofollow">ÜB 2</a>: Aussagenlogik</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt2-lsg.pdf">Lsg</a></td> <td><abbr title="Kurze konjunktive Normalform">KKNF</abbr>, <abbr title="Binary decision diagram">BDD</abbr>, Shannon Graphen</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt3.pdf" rel="nofollow">ÜB 3</a>: Aussagenlogik, PL1</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt3-lsg.pdf">Lsg</a></td> <td>DNF, KNF, DPLL</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt4.pdf" rel="nofollow">ÜB 4</a>: PL1</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt4-lsg.pdf">Lsg</a></td> <td>PL1 (Variante des Zebrarätsels); Unifikation</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt5.pdf" rel="nofollow">ÜB 5</a>: PL1</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt5-lsg.pdf">Lsg</a></td> <td>Verwandschaftsbeziehungen; (Java) Integer; Interpretation/Modell/Formel; Erfüllbar / allgemeingültig / unerfüllbar</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt6.pdf" rel="nofollow">ÜB 6</a>: PL1</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt6-lsg.pdf">Lsg</a></td> <td>Pränexnormalform; Skolemnormalform (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/09PK1Normalform-print.pdf" rel="nofollow">09</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt7.pdf" rel="nofollow">ÜB 7</a>: PL1, Aussagenlogik</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt7-lsg.pdf">Lsg</a></td> <td>Hilbertkalkül (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/11Hilbert.pdf">11</a>); Resolutionskalkül (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/12ALResolution-print.pdf">12</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt8.pdf" rel="nofollow">ÜB 8</a>: PL1</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt8-lsg.pdf">Lsg</a></td> <td>Resolutionskalkül, Tableaukalkül (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/13PK1Resolution-print.pdf">13</a>, <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/14Tableau-print.pdf" rel="nofollow">14</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt9.pdf" rel="nofollow">ÜB 9</a>: PL1, Aussagenlogik</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt9-lsg.pdf">Lsg</a></td> <td>Resolutionskalkül, Sequenzenkalkül (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/19PL1Sequenz-print.pdf" rel="nofollow">19</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt10.pdf" rel="nofollow">ÜB 10</a>: JML</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt10-lsg.pdf">Lsg</a></td> <td>Klassen-Invarianten; Methoden-Vertrag; Spezifikation</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt11.pdf" rel="nofollow">ÜB 11</a>: Reduktionssysteme</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt11-lsg.pdf">Lsg</a></td> <td>reflexive, transitive Hülle; (lokal) konfluent; noetersch; irreduzibel; Ackermann-Funktion; noethersche Induktion (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/22Reduktion-print.pdf" rel="nofollow">22</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt12.pdf" rel="nofollow">ÜB 12</a>: Modallogik</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt12-lsg.pdf">Lsg</a></td> <td>Kripke-Strukturen (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/27Modal-print.pdf" rel="nofollow">27</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt13.pdf" rel="nofollow">ÜB 13</a>: Büchi-Automaten</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt13-lsg.pdf">Lsg</a></td> <td>\(\omega\)-Sprachen, \(\omega\)-reguläre Ausdrücke (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/41Automaten-print.pdf" rel="nofollow">41</a>, <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/42buechiAut-print.pdf" rel="nofollow">42</a>)</td> </tr> <tr> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt14.pdf" rel="nofollow">ÜB 14</a>: LTL</td> <td><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt14-lsg.pdf">Lsg</a></td> <td>LTL-Formeln und Büchi-Automaten (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/43LTL-print.pdf" rel="nofollow">43</a>, <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/45LTL2Buechi-print.pdf" rel="nofollow">45</a>)</td> </tr> </table> <h3 id="jml">JML</h3> <p>Ein paar Auszüge aus den Folien von Prof. Dr. Beckert. Ich finde daran sieht man schön, wie JML funktioniert:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">PostInc</span>{ <span style="color:#088;font-weight:bold">public</span> PostInc rec; <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">int</span> x, y; <span style="color:#777">/*@ public invariant x &gt;= 0 &amp;&amp; y &gt;= 0 &amp;&amp; @ rec.x &gt;= 0 &amp;&amp; rec.y &gt;= 0; @*/</span> <span style="color:#777">/*@ public normal_behavior @ requires true; @ ensures rec.x == \old(rec.y) &amp;&amp; @ rec.y == \old(rec.y) + 1; @*/</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">void</span> postinc() { rec.x = rec.y++; } } </pre></div> </div> </div> <p>Quelle: <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/28JML.pdf#page=3">28JML.pdf#page=3</a></p> <p>Wichtig ist noch:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/*@ @ assignable \nothing; @ ensures (\forall int j; l &lt;= j &amp;&amp; j &lt; \result; a1[j] != a2[j] ); @*/</span> </pre></div> </div> </div> <p>Das <code>assignable \nothing</code> besagt, dass keine Werte (nach außen sichtbar) verändert werden dürfen.</p> <p>Die Schleifen-Syntax ist <code>\forall int i; B; R</code>, wobei <code>B</code> eine Bereichseinschränkung und <code>R</code> der Schleifenrumpf ist. Es gibt auch noch <code>\exists int i; B; R</code>.</p> <p>Die Prädikatenlogischen Operatoren sind</p> <ul> <li><code>!</code>: Negation</li> <li><code>&amp;&amp;</code>: und</li> <li><code>||</code>: oder</li> <li><code>==&gt;</code>: Implikation</li> <li><code>&lt;==&gt;</code>: Äquivalenz</li> <li><code>==</code>: Gleichheit</li> </ul> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">int</span> commonEntry(<span style="color:#339;font-weight:bold">int</span> l, <span style="color:#339;font-weight:bold">int</span> r) { <span style="color:#339;font-weight:bold">int</span> k = l; <span style="color:#777">/*@ loop_invariant @ l &lt;= k &amp;&amp; k &lt;= r &amp;&amp; @ (\forall int i; l&lt;=i &amp;&amp; i&lt;k; a1[i] != a2[i]); @ assignable \nothing; @ decreases a1.length - k; @*/</span> <span style="color:#080;font-weight:bold">while</span>(k &lt; r) { <span style="color:#080;font-weight:bold">if</span>(a1[k] == a2[k]){<span style="color:#080;font-weight:bold">break</span>;} k++; } <span style="color:#080;font-weight:bold">return</span> k; } </pre></div> </div> </div> <p>Quelle: <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/28JML.pdf#page=44">28JML.pdf#page=44</a></p> <h3 id="modallogik">Modallogik</h3> <table> <tr> <th>Interpretation</th> <th>\(\square A\) bzw. \(\square_p A\)</th> <th>\(\diamond A\)</th> </tr> <tr> <td></td> <td>A ist notwendigerweise wahr</td> <td>A ist m&ouml;glicherweise wahr</td> </tr> <tr> <td>Zeit</td> <td>A ist zu jedem zuk&uuml;nfigem Zeitpunkt wahr</td> <td>Es gibt einen zuk&uuml;nftigen Zeitpunkt zu dem A wahr ist</td> </tr> <tr> <td>Glauben</td> <td>Ein Agent p glaubt A</td> <td>A ist konsistent mit den Aussagen, die p f&uuml;r wahr h&auml;lt</td> </tr> <tr> <td>Wissen</td> <td>Ein Agent p wei&szlig; A</td> <td>p wei&szlig; nicht, dass A falsch ist</td> </tr> <tr> <td>Programmausf&uuml;hrung</td> <td>Nach Ausf&uuml;hrung des Programs p gilt A</td> <td>Es gibt eine Ausf&uuml;hrung des Programs p, nach der A wahr ist</td> </tr> </table> <h3 id="kurz-und-gut">Kurz und Gut</h3> <p>Die folgenden Stichpunkte sollte man (größtenteils nur sinngemäß) auswendig können und verstehen:</p> <ul> <li>Eine Signatur \(\Sigma\) ist eine abzählbare Menge von Symbolen. Die Elemente der Signatur heißen “Aussagevariablen”.</li> <li>Eine Interpretation ist eine Abbildung \(I: \Sigma \rightarrow {W, F}\)</li> <li>Ein Modell einer Formel \(A \in For0_\Sigma\) ist eine Interpretation \(I\) mit \(val_I(A) = W\).<br /> Ein Modell einer Formel ist also einfach eine Variablenbelegung, welche die Formel erfüllt.</li> <li>Für \(M \subseteq For0_\Sigma, A \in For0_\Sigma\) gilt: \(M \models A\) (lies: aus M folgt A), falls jede Variablenbelegung, welche \(M\) erfüllt, auch \(A\) erfüllt.</li> <li>\(A \rightarrow B \equiv \neg A \lor B\)</li> <li>\(A \models B\) gdw. \(\models A \rightarrow B\)</li> <li>Der shannon-Operator \(sh(a,b,c)\) ist if(a) {c} else {b}.</li> <li>Die Craig-Interpolation von \(A \rightarrow B\) ersetzt alle Aussagevariablen \({\text{Aussagevariable } a \in A | a \notin B}\) mit \(c_i\) (\(i=1,\dots,n\)). Die Interpolante ist dann \(C := \bigvee_{(c_1, \dots, c_n) \in {0,1}^n} A[c_1, \dots, c_n]\).</li> <li>Eine DNF heißt “vollständig” bzgl. einer Signatur \(\Sigma\), wenn falls für jedes \(P \in \Sigma\) in jeder Klausel entweder \(P\) oder \(\neg P\) vorkommt.</li> <li>Eine DNF heißt “minimal”, wenn jede kürzere Formel nicht äquivalent ist.</li> <li>KKNF-Konstruktion: (1) Shortcuts \(Q_1, \dots, Q_n\) für binäre Operatoren erstellen. Diese Shortcuts dürfen auch andere Shortcuts verwenden (2) Äquivalenzen auflösen (3) In KNF umformen.</li> <li>\(sh(P_i, A, B)\) heißt normiert, wenn \(A\) und \(B\) normiert sind und jede in \(A \cup B\) vorkommende Variable \(P_j\) gilt \(i &lt; j\).</li> <li>Ein Shannon-Graph heißt reduziert, wenn es keine zwei Knoten \(v,w\) gibt, sodass die beiden in \(v\) und \(w\) verwurzelten Teilbäume isomorph sind und es auch keinen Knoten gibt, bei dem beide ausgehenden Kanten in den selben Nachfolger führen.</li> <li>Reduzierter Shannon-Graph = OBDD = BDD = ordered binary decisio diagram</li> <li>Bei gegebener Indizierung sind reduzierte Shannon-Graphen bis auf Isomorphie eindeutig. Ist die Indizierung nicht gegeben, macht die Variablenanordnung einen großen Unterschied in der Größe (Knotenmenge) des reduzierten Shannon-Graphen.</li> <li>Multiplikation \(k\)-stelliger Binärzahlen: Für jede Ordnung \(&lt;\) der Variablen in \(X={x_0, \dots, x_{k-1}, y_0, \dots, y_{k-1}}\) gibt es einen Index \(0 \leq i &lt; 2k\), sodass der BDD \(B_{Mult_i,&lt;}\) mindestens \(2^{k/8}\) Knoten besitzt.</li> <li>Horn-Formel: Formel in KNF, wobei jede Klausel höchstens ein positives Literal enthält.</li> <li>Negationsnormalform: Negationen nur vor Atomen.</li> <li>Bereinigte Formel: (1) \(Frei(A) \cap Bd(A) = \emptyset\) (2) Die hinter Quantoren stehenden Variablen sind paarweise verschieden.</li> <li>Pränexe Normalform: \(A = Q_1 x_1 Q_2 x_2 Q_3 x_3 \dots Q_n x_n B\), wobei \(B\) quantorenfrei sein muss. Dann heißt \(B\) die Matrix von \(A\).</li> <li>Die Pränexe Normalform ist nicht eindeutig.</li> <li>Skolem-Normalform: (1) geschlossene Formel (2) \(\forall x_1 \dots \forall x_n B\) (3) Matrix \(B\) ist in KNF</li> <li><a href="https://de.wikipedia.org/wiki/G%C3%B6delscher_Vollst%C3%A4ndigkeitssatz">Gödelscher Vollständigkeitssatz</a>: Es gibt einen Kalkül der PL1 derart, dass für jede Formelmenge \(\Gamma\) und für jede Formel \(\varphi\) gilt: \(\varphi\) folgt genau dann aus \(\Gamma\), wenn \(\varphi\) im Kalkül aus \(\Gamma\) hergeleitet werden kann. In Zeichen: \(\Gamma \models \varphi \Leftrightarrow \Gamma \vdash \varphi\).</li> <li><a href="https://de.wikipedia.org/wiki/G%C3%B6delscher_Unvollst%C3%A4ndigkeitssatz">Gödelscher Unvollständigkeitssatz</a>: <ul> <li>Jedes hinreichend mächtige, rekursiv aufzählbare formale System ist entweder widersprüchlich oder unvollständig.</li> <li>Jedes hinreichend mächtige konsistente formale System kann die eigene Konsistenz nicht beweisen.</li> </ul> </li> <li>Kompaktheitssatz: Wenn A aus einer unendlichen Teilmenge der Formelmenge folgt, dann auch aus einer endlichen.</li> <li>Endlichkeitssatz: Eine Menge \(M \subseteq For_\Sigma\) hat genau dann ein Modell, wenn jede endliche Teilmenge von \(M\) ein Modell hat.</li> <li>Der Resolutionskalkül arbeitet nur mit Formeln in Skolemnormalform.</li> <li>Tableau-Kalkül: <ul> <li>Typ-\(\alpha\): Alles, was keine Quantoren hat und eindeutig ist</li> <li>Typ-\(\beta\): Alles, was keine Quantoren hat, aber nicht eindeutig ist</li> <li>Typ-\(\gamma\): Unendlich viele</li> <li>Typ-\(\delta\): min. eines</li> </ul> </li> <li>Ob eine prädikatenlogische Formel allgemeingültig ist, ist unentscheidbar.</li> <li>Die Menge der allgemeingültigen prädikatenlogischen Formeln ist rekursiv aufzählbar.</li> <li>Die Menge der erfüllbaren prädikatenlogischen Formeln ist nicht rekursiv aufzählbar.</li> <li>Ein Reduktionssystem ist ein Tupel \((D, \succ)\), wobei \(D \neq \emptyset\) eine Menge ist und \(\succ\) eine Relation auf \(D\) ist.</li> <li>\(\rightarrow\) bezeichnet die reflexive, transitive Hülle von \(\succ\).</li> <li>\(\stackrel{+}{\rightarrow}\) bezeichnet die transitive Hülle von \(\succ\).</li> <li>\(\leftrightarrow\) bezeichnet die reflexive, transtive und symmetrische Hülle von \(\succ\).</li> <li>\((D, \succ)\) heißt konfluent \(:\Leftrightarrow \forall s_1, s_2, s_3 \in D\) mit \(s \rightarrow s_1 \land s \rightarrow s_2 \exists t \in D: s_1 \rightarrow t \land s_2 \rightarrow t\)</li> <li>\((D, \succ)\) heißt lokal konfluent \(:\Leftrightarrow \forall s_1, s_2, s_3 \in D\) mit \(s \succ s_1 \land s \succ s_2 \exists t \in D: s_1 \rightarrow t \land s_2 \rightarrow t\)</li> <li>\((D, \succ)\) heißt noethersch, wenn es keine unendlichen Folgen \(s_0 \succ s_1 \dots \succ s_i \succ \dots\) gibt.</li> <li>Ein konfluentes und noethersches Reduktionssystem heißt kanonisch.</li> <li>Ein Element \(s \in D\) heißt irreduzibel (oder eine Normalform) in \((D, \succ)\), wenn kein \(t \in D\) existiert mit \(s \succ t\).</li> <li>Sei \(s \in D\). Ein Element \(s_0 \in D\) heißt eine Normalform für \(s\) in \((D, \succ)\), wenn \(s_0\) irreduzibel ist und \(s \rightarrow s_0\) gilt.</li> <li>In kanonischen Reduktionssystemen hat jedes Element eine eindeutige Normalform.</li> <li>\((D, \succ)\) ist noethersch und lokal konfluent \(\Rightarrow (D, \succ)\) ist konfluent.</li> <li>Eine Kripke-Struktur ist ein Tupel \(\mathscr{K} = (S, R, I)\) mit <ul> <li>\(S \neq \emptyset\) ist die Menge der Zustände bzw. der möglichen Welten. \(s \in S\) heißt also auch eine “Welt”.</li> <li>\(R \subseteq S \times S\) ist die Zugänglichkeitsrelation</li> <li>\(I: (\Sigma \times S) \rightarrow {W, F}\) ist die Interpretation der Aussagenlogischen Variablen</li> </ul> </li> <li>\((S, R)\) heißt der Kripke-Rahmen von \(\mathscr{K}\).</li> <li>\(\square A \rightarrow A\) ist nur in reflexiven Kripke-Strukturen eine Tautologie.</li> <li>Ein endlicher Automat ist ein Tupel \((S, V, \delta, s_0, S_1)\), wobei <ul> <li>\(S\) eine endliche Zustandsmenge ist,</li> <li>\(V\) ein endliches Alphabet (terminale Zeichen) ist,</li> <li>\(\delta: S \times V \rightarrow S\) eine Funktion ist, die besagt bei welchem Eingabezeichen man von welchem Zustand aus in welchen Zustand kommt,</li> <li>\(s_0 \in S\) ein Startzustand und</li> <li>\(S_1 \subseteq S\) die Menge der Endzustände ist</li> </ul> </li> <li>\(V^\omega\) ist die Menge der unendlichen Wörter mit Buchstaben aus \(V\).</li> <li>\(w(n)\) ist der \(n\)-te Buchstabe des Wortes \(w\).</li> <li>\(w \downarrow (n)\) ist das endliche Anfangsstück \(w(0)\dots w(n)\) von \(w\).</li> <li>\(\varepsilon \notin V^\omega\)</li> <li> <table> <tbody> <tr> <td>Für \(K \in V^*\) und \(J \in V^\omega\) ist \(KJ={w_1 w_2</td> <td>w_1 \in K, w_2 \in J}\)</td> </tr> </tbody> </table> </li> <li> <table> <tbody> <tr> <td>Für \(K \in V^*\) ist \(\overset{\rightarrow}{K}={w \in V^\omega</td> <td>w \downarrow (n) \in K \text{ für unendlich viele } n}\)</td> </tr> </tbody> </table> </li> <li>Ein Büchi-Automat ist ein nicht deterministischer endlicher Automat, der Wörter akzeptiert, wenn es eine Berechnungsfolge mit unendlich vielen Finalzuständen gibt. (vgl. <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/42buechiAut-print.pdf#page=6">Beispiel</a>)</li> <li>A <strong>U</strong> B: A gilt, bis B gilt (das U steht für “until”). Allerdings gilt B auch irgendwann. Es kann also nicht sein, dass A unendlich lange gilt und B nie.</li> <li>\(A\;\textbf{U}_W\;B\) bedeutet, dass entweder immer A und gleichzeitig nie B gilt, oder dass irgendwann B gilt und davor gilt immer A. Das ‘W’ steht für ‘weak’.</li> <li>\(A\;\textbf{V}\;B\): B gilt so lange, bis A gilt. Daher wird V auch ‘Release-Operator’ genannt.</li> <li>\(\diamond \square P\): Es gibt einen Zeitpunkt, ab dem immer B gilt.</li> <li>Zu jeder LTL-Formel gibt es einen effektv konstruierbaren Büchi-Automaten.</li> <li>Erfüllbarkeit und Allgmeingültigkeit von LTL-Formeln ist entscheidbar.</li> <li>Ein Kalkül ist korrekt, wenn alles was formal ableitbar auch wahr ist. (vgl. <a href="https://de.wikipedia.org/wiki/Korrektheit_(Logik)">Korrektheit (Logik)</a>)</li> <li>08Pk1Semantik-print.pdf, Folie 34/37: QxB steht für “Quantor x B”, wobei der Quantor entweder \(\exists\) oder \(\forall\) ist, \(x\) eine Variable ist und \(B\) eine Formel ist.</li> </ul> <h2 id="wissens-check">Wissens-Check</h2> <p>Folgende Fragen sollte man für die Klausur schnell beantworten können:</p> <ul> <li>Nenne 3 Basen für die Aussagenlogik. Eine davon soll höchstens einen Operator haben.</li> <li>In welcher Komplexitätsklasse ist das Erfüllbarkeitsproblem für 3-KNF? In welcher 2-KNF? Wie sieht es mit dem Allgemeingültigkeitsproblemen aus?</li> <li>Was ist der Shannon-Graph von \(1\)?</li> <li>Was ist der Shannon-Graph von \(0\)?</li> <li>Was ist der Shannon-Graph von \(a \lor b\)?</li> <li>Was ist der Shannon-Graph von \(a \land b\)?</li> </ul> <h2 id="meine-fragen">Meine Fragen</h2> <ul> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/02ALIntro-print.pdf">02, Folie 19/29</a>: Warum wird einmal \(\models\) und dann \(\models_\Sigma\) geschrieben?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/07PK1Intro-print.pdf#page=19">07, Folie 19/51</a>: Warum “fast alle” \(x \in Var\)? Was bedeutet das? <ul> <li>Es dürfen nur endlich viele Variablen umbenannt bzw. durch einen Term ersetzt werden. Andernfalls werden die Beweise und Notationen hässlich. Abzählbar unendlich viele Variablen sind praktisch, wenn man sich die Existenz immer weiterer Variablen sichern will, die nicht in einer gegebenen Formel auftauchen. Natürlich ist jede Formel endlich, enthält also nur endlich viele Variablen.</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/09PK1Normalform-print.pdf#page=8">Folie 8/30</a>: Wieso stimmt diese Umformung? <ul> <li>Gebundene Variablen dürfen unabhängig von freien umbenannt werden. Die andere Umformung kann nachvollzogen werden, wenn die Implikation \(A \rightarrow B\) zu \(\neg A \vee B\) umgeformt wird. Man beachte folgende Umformungsregel: \(\neg \forall x F(x) \equiv \exists x \neg F(x)\).</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/09PK1Normalform-print.pdf#page=23">Folie 23/30</a>: Was ist eine Grundinstanz? Wo ist der Unterschied zwischen “Grundinstanz” und “Instanz”? Was sind “Grundterme”? <ul> <li>Grundterm: Ein Term, der keine Variablen enthält. Instanz: Für quantifizierte Variablen wurden Terme eingesetzt. Grundinstanz: Für alle Variablen wurden Grundterme eingesetzt. Damit enthalten Grundinstanzen überhaupt keine Variablen mehr.</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/09PK1Normalform-print.pdf#page=24">Folie 24/30</a>: Was ist ein Beispiel für \(D = Term_\Sigma^0 \neq\) Menge der Grundterme? Wo gilt 2. nicht? <ul> <li>Ich vermute mal, dass \(Term_\Sigma^0 := \) Menge der Grundterme. Bachte (sofern die Definition stimmt): \(Term_\Sigma^0 \subseteq Term_\Sigma\), da es auch Terme gibt, die Variablen enthalten, falls welche in der Signatur vorhanden sind. Was ist die Bedeutung von Herbrand-Strukturen / dem Satz von Herbrand?</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt6-lsg.pdf">Blatt 6, Lösung zu Aufgabe 4</a>: Den Teil mit der Umwandlung einer Aussagenlogischen Formel verstehe ich nicht. Kann das jemand bitte für \(a \land \neg b \lor c \lor d\) erklären?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt9-lsg.pdf">Blatt 9, Lösung zu Aufgabe 1</a>: Ist der Baum, also insbesondere die ersten 4 Knoten, richtig? Warum steht in Knoten 1 nicht \(1\forall x \forall y \forall z (r(x,y) \land r(y,z) \rightarrow r(x,z))\)? Wie funktioniert der 1. Schritt in Aufgabe 2?</li> <li>Haben reflexive Relationen irreduzible Elemente? <ul> <li>Laut unserer Definition nicht. Aber du kannst jede n-stellige Relation mit dem Komplement der n-stelligen Gleichheits-Relation schneiden, dann erhältst du ihr irreflexives Gegenstück.</li> </ul> </li> <li>Können reflexive Relationen noethersch sein? <ul> <li>Nur, wenn sie leer sind. Ansonsten gibt es immer unendliche Ketten.</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/27Modal-print.pdf#page=27">Folie 27</a>: Wie muss ich \(\square \diamond P\) lesen? <ul> <li>Von jeder erreichbaren Welt aus gibt es eine erreichbare Welt, in der P gilt. Die Verbalisierung der Relation “erreichbar” klappt immer ;)</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt12-lsg.pdf">Blatt 12, Aufgabe 1b</a>: Was sagt \(\diamond\square P\) auf dem Graphen aus? Insbesondere: Warum ist \(w_5\) nicht in \(\diamond\square P\)? Was wäre \([[\square \diamond P]]\)?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt12.pdf">Blatt 12, Aufgabe 4</a>: Das muss ich noch mal in Ruhe durchgehen.</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/21Peano-print.pdf#page=8">21, Folie 8</a>: Was ist \(Th(N)\) und was ist \(Cn(PA)\)? <ul> <li>\(Th(N)\): Theoreme über N, also die Menge aller Formeln, für die die natürlichen Zahlen ein Modell sind. Cn(PA): Menge aller Formeln, die aus den Axiomen der Peano-Artihmetik gefolgert werden können. Da die Peano-Arithmetik korrekt ist, ist jede Formel aus Cn(PA) auch in Th(N).</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/50Wiederholung-print.pdf#page=16">50, Folie 16</a>: Was bedeutet es, dass \(Th(N)\) nicht rekursiv ist? <ul> <li>Rekursiv heißt entscheidbar. Da die Peano-Axiome durch die Peano-Artihmetik formalisiert werden können, gibt es eine Formel P(x), die genau dann wahr ist, wenn für x die Kodierung einer solchen Formel eingesetzt wird, die sich nicht aus den Peano-Axiomen herleiten lässt. Nach dem Gödelschen Unvollständigkeitssatz gibt es nun eine Formel P und x derart, dass x mit der Kodierung von P(x) übereinstimmt: Eine Formel also, die über sich selbst behauptet, sie sei nicht herleitbar. Da es nur ein Modell gibt, ist jede Formel entweder unerfüllbar oder allgemeingültig. Wenn \(Th(N)\) entscheidbar wäre und P(x) allgemeingültig, dann entsteht Widerspruch zur Wahl von P und x. Wenn P(x) unerfüllbar wäre, ist nach Wahl von P und x P(x) herleitbar, was wieder einen Widerspruch darstellt. Um den Widerspruch aufzulösen, darf “aus den PA-Axiomen herleitbar” nicht mit “im Modell der nat. Zahlen gültig” übersetzt werden.</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/23Termersetzung-print.pdf#page=5">23, Folie 5</a>: Kann mir jemand ein konkretes Beispiel geben?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/43LTL-print.pdf#page=2">43, Folie 2</a>: Was sind omega-Strutkuren und insbesondere was bedeutet \(2^P\)? <ul> <li>Eine Omega Struktur Ordnet jedem Zeitpunkt, wenn die natürlichen Zahlen als Zeitstrahl aufgefasst werden, eine Menge von aussagenlogischen Variablen zu, die als “wahr” gelten sollen. \(2^P\) ist die Potenzmenge von P.</li> </ul> </li> <li>Ist \(A\;\textbf{U}_W\;B\) äquivalent zu \(B\;\textbf{V}\;A\)?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt14-lsg.pdf">Blatt 14, 2a</a>: Warum ist \(\diamond (p\;\textbf{U}\;q)\) äquivalent zu \(\diamond q\)? Ich dachte es wäre äquivalent zu \(p\;\textbf{U}\;q\)?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt14-lsg.pdf">Blatt 14, 3</a>: Wie würde der Automat aussehen, wenn das \(X\) weggelassen würde?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/blatt14-lsg.pdf">Blatt 14, 4</a>: Das würde ich gerne gemeinsam durchgehen.</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/50Wiederholung-print.pdf#page=13">50, 13</a>: Was sind die Ziele der Beweistheorie? Was ist die Grundidee des Hilbert-Kalküls? <ul> <li>Ziele: Automatisches Beweisen ermöglichen und die Grenzen bestimmen. Grundidee des Hilbert-Kalküls: Aus Axiomen konstruktiv Formeln folgern. Im Gegensatz zu den praxis-orientierten Beweisverfahren kann der Hilbert-Kalkül leichter in theoretischen Beweisen verwendet werden. Der Gödelsche Unvollständigkeitssatz verwendet z.B. den Hilbert-Kalkül.</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/50Wiederholung-print.pdf#page=13">50, 13</a>: “Aussagenlogische Tableauregeln aus Wahrheitstafeln konstruieren.” - was ist damit gemeint?</li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/50Wiederholung-print.pdf#page=15">50, 15</a>: Was ist die Grundidee der Peano-Arithmetik? <ul> <li>Liegt doch eigentlich auf der Hand: Zahlentheoretische Aussagen automatisch beweisen.</li> </ul> </li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/50Wiederholung-print.pdf#page=33">50, 33</a>: Wie kann man sich in dem Beispiel den Unterschied zwischen Prädikaten und Funktionen erschließen? <ul> <li>Funktionen sind immer in Prädikaten enthalten. Ein Prädikat darf kein weiteres Prädikat enthalten.</li> </ul> </li> <li>Wie ist Erfüllbarkeit in der Prädikatenlogik definiert? Z.B. erscheint mir \(\exists x p(x)\) erfüllbar, wenn nichts weiter gegeben ist. Wenn man aber \(p(x)=False\) für alle \(x\) sagt, dann ist es unerfüllbar. <ul> <li>F ist erfüllbar gdw. es ein Modell für F gibt, d.h. eine Interpretation I, sodass val_I(F) = W.</li> </ul> </li> <li>Müssen die Kanten von Shannon-Graphen mit W und F oder mit 1 und 0 beschriftet werden? Praktisch alle Altklausuren verwenden 1 und 0, aber ich meine er hätte in der Vorlesung gesagt, dass wir W und F verwenden sollen.</li> <li>Ist die Menge der allgemeingültigen / erfüllbaren / unerfüllbaren Formeln der PL1 abzählbar? Jede Teilmenge aus \(\Sigma^*\) ist abzählbar für ein endliches Alphabet \(\Sigma\). Es gibt aber überabzählbar viele Teilmengen, deren Elemente zwar wieder abzählbar sind, aber sowohl die Teilmengen selbst als auch ihre Elemente nicht aufzählbar sind. Beachte: Aufzählbar \(\neq\) Abzählbar.</li> <li>Wie kann man \(U\) durch \(U_W\) darstellen?</li> </ul> <h2 id="altklausuren">Altklausuren</h2> <ul> <li>WS2010/2011, 1. Zwischentest, A4: Ist der Markierungsalgorithmus für Hornformeln relevant?</li> <li>WS2010/2011, 2. Zwischentest, A1: <ul> <li>Was ist eine kompakte Logik? (PL2 ist laut WS2008/2009, 2.Zwischentest 1b, nicht kompakt)</li> <li>Was bedeutet \(Cl_{\exists}(t_1 \doteq t_2)\)?</li> </ul> </li> <li>WS2009/2010, A1c: Wieso gibt es für \(\exists p(x)\) kein Herbrandmodell?</li> <li>WS2009/2010, 1.Zwischentest <ul> <li>A1a: Was ist ein “Vereinfachungsschritt” im Davis-Putnam-Verfahren? Was bedeutet es, wenn dort keine Klausel mehr zur Verfügung steht?</li> <li>A1a: “Wenn A und B erfüllbar sind, dann ist auch \(A \rightarrow B\) erfüllbar.” - Was ist mit \(B = \neg A\)?</li> </ul> </li> <li>WS 2009/2010, 2. Zwischentest (ist beim ersten): <ul> <li>A1a: Warum ist \(\forall x \forall y (x \leftrightarrow y)\) keine Formel der PL1?</li> <li>A4: Will ich gerne durchsprechen</li> </ul> </li> <li>WS 2008/2009: <ul> <li>1a: Warum ist \(\forall x (p(x) \rightarrow q(p(x)))\) keine Formel der PL1?</li> <li>1a: Warum ist \(\exists x (p(x) \rightarrow p(f(x)))\) allgemeingültig?</li> <li>1b: Was ist ein Beispiel für einen Büchi-Automaten, für den es keinen deterministischen Büchi-Automaten gibt?</li> <li>1b: “Für jede geschlossene prädikatenlogische Formel G gilt: Es gibt ein Modell für G oder für das Negat von G oder für beide.” - Gilt das nicht für alle prädikatenlogischen Formeln (egal ob geschlossen oder nicht)?</li> </ul> </li> <li>WS 2008/2009, 1. Zwischentest: <ul> <li>1a: Wie lange dauert der kürzeste Resoultionsbeweis in Anzahl der Literale?</li> <li>1b: Warum gibt es keine prädikatenlogische Interprätation, in der alle prädikatenlogischen Formeln wahr sind?</li> </ul> </li> </ul> <h2 id="material">Material</h2> <ul> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/skriptum.pdf">Skript</a></li> <li><a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/">Vorlesungswebsite</a></li> <li><a href="https://www.fsmi.uni-karlsruhe.de/Pruefungen/Schriftlich.html">Altklausuren</a></li> </ul> <p>StackExchange:</p> <ul> <li><a href="http://math.stackexchange.com/q/1150746/6876">What is the operator precedence for quantifiers?</a></li> <li><a href="http://math.stackexchange.com/q/1150826/6876">How do you bring quantors to the front of a formula?</a></li> <li><a href="http://math.stackexchange.com/a/214352/6876">How to convert to conjunctive normal form?</a></li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <ul> <li>Wo sind die Übungsblätter: <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/">Link</a></li> <li>Abgabeform: Keine Abgabe</li> <li>Turnus: wöchentlich</li> <li>Lösungen: Die Lösungen von jeweils zwei Blättern werden dann in den 14-tägig stattfinden Übungen am Freitag besprochen.</li> <li>Übungsschein verpflichtend: Es gibt keinen Übungsschein.</li> <li>Bonus durch Übungsschein: Es gibt keinen Klausurbonus durch Übungsblätter.</li> <li>Anderer Klausurbonus: Man kann durch insgesammt 4 Zwischentests und 2 Praxisaufgaben für die wirkliche Klausur Punkte sammeln. Die Teilnahme an den Zwischentests und den Praxisaufgaben ist freiwillig. Die erzielten Übungspunkte werden im Verhältnis 1:10 als Bonuspunkte auf die bestandene Abschlussklausur angerechnet.</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p>Siehe <a href="http://www.informatik.kit.edu/klausuren.php">Klausurtermine-Seite</a> für zukünftige Termine.</p> <p><strong>Datum</strong>: Freitag, den 6. März 2015 von 11:00 bis 12:00 Uhr (<a href="http://formal.iti.kit.edu/teaching/FormSysWS1415">Quelle</a>).<br /> <strong>Ort</strong>: Gerthsen (<a href="http://www.kithub.de/map/2287">30.21</a>) und HSaF (<a href="http://www.kithub.de/map/2222">50.35</a>) - vgl. <a href="http://formal.iti.kit.edu/teaching/FormSysWS1415/klausur1.html">Anmeldeliste</a><br /> <strong>Punkte</strong>: 60<br /> <strong>Punkteverteilung</strong>: ? (Stand: 06.03.2015)<br /> <strong>Bestehensgrenze</strong>: ? (Stand: 06.03.2015)<br /> <strong>Übungsschein</strong>: Gibt es nicht.<br /> <strong>Bonuspunkte</strong>: Bis zu 8. Die Punkte aus den 4 Zwischenprüfungen und 2 Praxisaufgaben werden addiert, dann durch 10 geteilt und schließlich kaufmännisch gerundet.<br /> <strong>Ergebnisse</strong>: Klausur wurde noch nicht geschrieben<br /> <strong>Einsicht</strong>: steht noch nicht fest (Stand: 06.03.2015)<br /> <strong>Erlaubte Hilfsmittel</strong>: Keine.</p> <h2 id="ergebnisse">Ergebnisse</h2> <p>Klausur wurde noch nicht geschrieben.</p> Gradient Descent, the Delta Rule and Backpropagation //martin-thoma.com/gradient-descent-delta-rule-backpropagation/ Sun, 26 Oct 2014 21:06:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/gradient-descent-delta-rule-backpropagation <p>If you learn about machine learning you will stumble over three terms that are related:</p> <ul> <li>Gradient descent,</li> <li>the Delta rule and</li> <li>backpropagation</li> </ul> <p>Gradient descent is a way to find a minimum in a high-dimensional space. You go in direction of the steepest descent.</p> <p>The delta rule is an update rule for single layer perceptrons. It makes use of gradient descent.</p> <p>Backpropagation is a special form of gradient descent, where a rule can be formulated which has some recursively defined parts. Those parts belong to neurons of different layers and get calculated from the output-layer (last layer) to the first hidden layer.</p> <h2 id="see-also">See also</h2> <p>Wikipedia pages:</p> <ul> <li><a href="https://en.wikipedia.org/wiki/Gradient_descent">Gradient descent</a></li> <li><a href="https://en.wikipedia.org/wiki/Delta_rule">Delta rule</a></li> <li><a href="https://en.wikipedia.org/wiki/Backpropagation">Backpropagation</a></li> </ul> On-line Handwriting Recognition of Mathematical Symbols //martin-thoma.com/write-math/ Fri, 17 Oct 2014 12:25:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/write-math <p>On-line handwriting recognition systems get the information how a symbol is written. In contrast, OCR only gets the pixel map.</p> <p>I’ve created a system that can be used to work with handwriting recognition systems in my bachelor’s thesis.</p> <h2 id="write-mathcom">write-math.com</h2> <p>The website <a href="http://write-math.com">write-math.com</a> was used to collect data. The source is at <a href="https://github.com/MartinThoma/write-math">github.com/MartinThoma/write-math</a>.</p> <h2 id="hwrt-toolkit">hwrt toolkit</h2> <p>The <a href="https://github.com/MartinThoma/hwrt"><code>hwrt</code></a> toolkit was created to work with on-line handwritten symbols. The toolkit is documented at <a href="https://pythonhosted.org/hwrt/">pythonhosted.org/hwrt</a>.</p> <p>The raw data can be downloaded with this toolkit.</p> <p>The toolkit can be used to classify data on your computer (without internet connection):</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/write-math-browser-ui.png"><img src="//martin-thoma.com/captions/write-math-browser-ui.png" alt="Write math: Interactive Browser Interface (offline)" width="500" height="400" class="" /></a><p class="wp-caption-text">Write math: Interactive Browser Interface (offline)</p></div> <h2 id="nntoolkit">nntoolkit</h2> <p>The <a href="https://github.com/MartinThoma/nntoolkit"><code>nntoolkit</code></a> was created to have a free software to create, train, test and evaluate neural networks.</p> <h2 id="hwr-experiments">HWR experiments</h2> <p>All experiments configuration files are saved in the project <a href="https://github.com/MartinThoma/hwr-experiments">github.com/MartinThoma/hwr-experiments</a>.</p> <h2 id="data">Data</h2> <p>The data can be downloaded from <a href="http://write-math.com/data">write-math.com/data</a>. I will try to keep a relatively recent version online. You can contact me if you want the latest version. However, I should note that currently (2015-04-12) this is about 3.7GB. This means sharing the data is not that easy.</p> <h2 id="presentations">Presentations</h2> <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/blob/master/presentations/Bachelor-Short/LaTeX/bachelor-short.pdf?raw=true">27.08.2014</a></li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/blob/master/presentations/Bachelor-Final-Presentation/LaTeX/Bachelor-Final-Presentation.pdf?raw=true">06.11.2014</a>: Final presentation for bachelor’s thesis</li> </ul> <h2 id="bachelors-thesis">Bachelor’s thesis</h2> <ul> <li><a href="http://arxiv.org/abs/1511.09030">07.11.2014</a>: My bachelor’s thesis. I’ve got the best grade (1.0) for it ☺. Please note that the submission to arxiv was later and a couple of typos were fixed as well as the term “data multiplication” was replaced by “data augmentation”.</li> <li><a href="http://digbib.ubka.uni-karlsruhe.de/volltexte/1000048047">29.06.2015</a>: An updated, condensed version of my bachelor’s thesis.</li> </ul> <h3 id="remarks">Remarks</h3> <ul> <li>What I called “data multiplication” is called “data augmentation” by others (e.g. <a href="http://www.cs.toronto.edu/~fritz/absps/imagenet.pdf">ImageNet Classification with Deep Convolutional Neural Networks</a>, <a href="http://arxiv.org/abs/1501.02876">Deep Image: Scaling up Image Recognition</a>, <a href="http://benanne.github.io/2015/03/17/plankton.html#data-augmentation">Classifying plankton with deep neural networks</a>)</li> </ul> 3D Printing //martin-thoma.com/3d-printing/ Sun, 28 Sep 2014 22:23:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/3d-printing <p>3D printing is a hot topic for quite a while now. 3D printers have become cheap enough so that many ordinary people can have 3D printers for their personal use. In this article, I would like to point out some very nice applications of 3D printing.</p> <h2 id="medicine">Medicine</h2> <p>3D printing has basically two application in medicine: Very customized non-organic parts or organic printing.</p> <h3 id="printing-a-human-kidney">Printing a human Kidney</h3> <iframe src="https://embed-ssl.ted.com/talks/anthony_atala_printing_a_human_kidney.html" width="560" height="315" frameborder="0" scrolling="no" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h3 id="magic-arms-prosthetic">“Magic Arms” prosthetic</h3> <iframe width="512" height="288" src="//www.youtube.com/embed/WoZ2BgPVtA0" frameborder="0" allowfullscreen=""></iframe> <h3 id="d-printing-gives-man-new-face">3D printing gives man new face</h3> <iframe width="512" height="288" src="//www.youtube.com/embed/5SWw_qM6_8I" frameborder="0" allowfullscreen=""></iframe> <h3 id="other-examples">Other examples</h3> <ul> <li><a href="https://en.wikipedia.org/wiki/Hearing_aid">Hearing aids</a></li> <li>Bones</li> <li>Print on wounds</li> </ul> <h2 id="shoes">Shoes</h2> <p>I am always struggling with finding good shoes. Most shoes I try feel unconfortable, although I have size 42 (which seems to be a very standard size in Germany for males). What if we could go to a store, let them 3D scan our feet and they automatically adjust a 3D model of a shoe to fit to our feet. Then some parts are 3D printed, assembled and a few days later we get a shoe that is customized to our feet and cheap.</p> <p><a href="http://www.continuumfashion.com/">continuumfashion.com</a> seems to 3D print shoes with Nylon. <a href="http://kobilevidesign.com/">kobilevidesign.com</a> is another designer who 3D prints shoes.</p> <h2 id="toys">Toys</h2> <ul> <li>Board game figures (e.g. custom chess sets, Monopoly cars, …)</li> <li>Model building (e.g. <a href="https://en.wikipedia.org/wiki/Ship_model">Ship model</a> where people pay A LOT of money for it)</li> <li>Lego</li> </ul> <h2 id="teaching">Teaching</h2> <p>Did you have chemistry in school and learn about atom models / crystaline structures? With 3D printing, it becomes easy to get those models for every student!</p> <p>Or think about architecture and history. You could show models of ancient cities or buildings in 3D.</p> <h2 id="spare-parts">Spare parts</h2> <p>Imagine something small breaks. Sometimes very expensive devices that are otherwise fine, become useless or at least ugly. Now think you could go online, download a 3D model of that part and just print it.</p> <h2 id="design">Design</h2> <ul> <li>Lamps</li> <li>Cups</li> </ul> <h2 id="weapons">Weapons</h2> <p>Sadly, 3D printing can also be used to produce weapons (<a href="https://en.wikipedia.org/wiki/Liberator_(gun)">source</a>).</p> <p>However, a 3D printed pistol has a high chance of not working at all, of hurting the person that created it and of working. So currently, it’s quite a lot of gambling. But that might change when the quality of 3D printing improves.</p> <h2 id="see-also">See also</h2> <ul> <li>Printers and Stuff <ul> <li><a href="https://www.indiegogo.com/projects/craftbot-3d-printer">CraftBot 3D printer</a>: An indiegogo project for an 3D printer that costs for about 315 Euro</li> <li><a href="https://www.indiegogo.com/projects/rapide-lite-affordable-high-resolution-3d-printer">Rapide Lite</a>: about 730 Euro, 50 micron resolution</li> <li><a href="https://www.indiegogo.com/projects/protocycler-free-sustainable-3d-printer-filament">ProtoCycler: Free, Sustainable 3D Printer Filament</a>: Another indigogo project, which aims to recycle plastics and create filaments yourself.</li> <li><a href="https://www.indiegogo.com/projects/rapide-lite-affordable-high-resolution-3d-printer/x/7191655">Rapide Lite</a>: Another 3D printer</li> <li><a href="https://www.kickstarter.com/projects/1853707494/pancakebot-the-worlds-first-pancake-printer">PancakeBot - The world’s first pancake printer!</a></li> <li><a href="https://www.kickstarter.com/projects/boxzy/boxzy-rapid-change-fablab-mill-laser-engraver-3d-p?ref=NewsApr0915&amp;utm_campaign=Apr+09&amp;utm_medium=email&amp;utm_source=newsletter">BoXZY</a></li> <li><a href="https://www.indiegogo.com/projects/nea-3d-stylish-upgradeable-3d-printing-for-all">NEA 3D</a></li> <li><a href="https://ember.autodesk.com/">Ember</a>: A 3D printer (DLP Stereolithography) for about 6000 US-Dollars (Z-Resolution of 10 microns, xy-resolution of 50 microns; 18 mm/hour at 25µm layers).</li> </ul> </li> <li>Engineering <ul> <li><a href="http://www.ted.com/talks/klaus_stadlmann_the_world_s_smallest_3d_printer">The Worlds smallest 3D printer</a></li> </ul> </li> <li>Medicine <ul> <li><a href="http://www.ted.com/talks/anthony_atala_printing_a_human_kidney">Printing a human kidney</a></li> <li><a href="http://www.ted.com/talks/lee_cronin_print_your_own_medicine">Print your own medicine</a></li> <li><a href="http://www.ted.com/talks/david_sengeh_the_sore_problem_of_prosthetic_limbs">The sore problem of prosthetic limbs</a></li> </ul> </li> <li>Models <ul> <li><a href="http://www.ted.com/talks/ben_kacyra_ancient_wonders_captured_in_3d">Ancient wonders captured in 3D</a></li> </ul> </li> <li>General 3D printing <ul> <li><a href="http://3dprintingindustry.com/3dpitv/">3dpi.tv</a></li> <li><a href="http://www.ted.com/talks/lisa_harouni_a_primer_on_3d_printing">A primer on 3D printing</a></li> <li><a href="https://en.wikipedia.org/wiki/Category:3D_printing">Category:3D printing</a></li> <li><a href="http://www.thingiverse.com/">MakerBot Thing-i-verse</a></li> <li><a href="http://www.digitalforming.com/">Digital Forming</a>: A company that allows you to customize 3D models</li> <li><a href="http://www.yobi3d.com/">yobi3d.com</a>: A database of 3D models</li> </ul> </li> <li>Applications: <ul> <li><a href="http://dornob.com/print-to-build-3d-printed-joints-make-it-easy-to-construct-furniture/">Print to Build: 3D-Printed Joints Make it Easy to Construct Furniture</a></li> </ul> </li> </ul> interACT //martin-thoma.com/interact/ Thu, 11 Sep 2014 17:25:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/interact <p>interACT is an exchange program for students. I’m a student from KIT (Germany) and I went to CMU in Pittsburgh (US). The information in the following article will be most useful for students who also come from KIT and want to go to CMU.</p> <h2 id="participating-universities">Participating universities</h2> <p>An interACT exchange is available between the following universities:</p> <ul> <li>United States: <ul> <li><a href="https://en.wikipedia.org/wiki/Carnegie_Mellon_University">CMU</a>, <a href="https://en.wikipedia.org/wiki/Pittsburgh">Pittsburgh</a> and <a href="https://en.wikipedia.org/wiki/Mountain_View,_California">Mountain View</a></li> <li><a href="https://en.wikipedia.org/wiki/University_of_Southern_California">USC</a> (<a href="https://en.wikipedia.org/wiki/Los_Angeles">Los Angeles</a>)</li> </ul> </li> <li>Germany: <a href="https://en.wikipedia.org/wiki/Karlsruhe_Institute_of_Technology">KIT</a> (<a href="https://en.wikipedia.org/wiki/Karlsruhe">Karlsruhe</a>)</li> <li>China: <a href="https://en.wikipedia.org/wiki/Hong_Kong_University_of_Science_and_Technology">HKUST</a> (<a href="https://en.wikipedia.org/wiki/Hong_Kong">Hong Kong</a>)</li> <li>Japan <ul> <li><a href="https://en.wikipedia.org/wiki/Waseda">Waseda University</a> (<a href="https://en.wikipedia.org/wiki/Tokyo">Tokyo</a>)</li> <li><a href="https://en.wikipedia.org/wiki/National_Institute_of_Information_and_Communications_Technology">NICT</a> (<a href="https://en.wikipedia.org/wiki/Tokyo">Tokyo</a>)</li> <li><a href="https://en.wikipedia.org/wiki/Nara_Institute_of_Science_and_Technology">NAIST</a> (<a href="https://en.wikipedia.org/wiki/Ikoma,_Nara">Ikoma</a>)</li> </ul> </li> <li>Spain: <a href="https://en.wikipedia.org/wiki/IIT_Madrid">IIT</a> (<a href="https://en.wikipedia.org/wiki/Madrid">Madrid</a>)</li> </ul> <h2 id="preparation">Preparation</h2> <p>You need to think about quite a lot for your preparation. This should give you an overview:</p> <h3 id="forms-and-other-general-stuff">Forms and other general stuff</h3> <ul> <li>bank statement</li> <li>send copy of passport to interACT</li> <li>visit US embassy</li> <li>get to know some people in the US before you get there</li> <li>transfer money on your VISA card to make sure you have enough when you’re there</li> <li>mobile: ultra.me is the best internet / phone provider!</li> <li>test internet calls (Skype / Google Hangouts) with parents and partner</li> <li>organize the flight after you have the Visa back</li> </ul> <h3 id="find-a-room">Find a room</h3> <ul> <li>Do you want to find a subleaser?</li> <li>Get a room in the US <ul> <li>http://sfbay.craigslist.org/</li> <li>eventually <a href="https://www.airbnb.de">airbnb.de</a> for the first nights</li> </ul> </li> </ul> <h3 id="health">Health</h3> <ul> <li>Get health insurance for the US <ul> <li>Signal Iduna</li> <li>barmenia.de: <ul> <li>http://www.barmenia.de/de/produkte/reiseversicherung/einzelreisen/reisekrankenversicherung.xhtml</li> <li>price: ca. 283 Euro</li> </ul> </li> <li>If you are also in the “Studienstiftung” you should have a look in “Daidalosnet”. There is a very good offer for health insurance</li> </ul> </li> <li>Go to all doctors you need in Germany right before you go to the US: <ul> <li>dentist</li> <li>Vaccination (I refreshed <a href="https://en.wikipedia.org/wiki/Tetanus">Tetanus</a>, <a href="https://en.wikipedia.org/wiki/Diphtheria">Diphtheria</a> and <a href="https://en.wikipedia.org/wiki/Pertussis">Pertussis</a> with a single injection)</li> </ul> </li> </ul> <h3 id="what-to-take-with-you">What to take with you</h3> <h4 id="cloths">Cloths</h4> <p>Check the weather and adjust the list to your needs. Don’t forget</p> <ul> <li>a raincoat</li> <li>warm cloths for the flight</li> </ul> <p>And, of course, don’t forget towels:</p> <blockquote> <p>Just about the most massively useful thing any interstellar Hitchhiker can carry. Partly it has great practical value. You can wrap it around you for warmth as you bound across the cold moons of Jaglan Beta; you can lie on it on the brilliant marble-sanded beaches of Santraginus V, inhaling the heady sea vapours; you can sleep under it beneath the stars which shine so redly on the desert world of Kakrafoon; use it to sail a miniraft down the slow heavy River Moth; wet it for use in hand-to-hand combat; wrap it round your head to ward off noxious fumes or avoid the gaze of the Ravenous Bugblatter Beast of Traal (a mind-bogglingly stupid animal, it assumes that if you can’t see it, it can’t see you — daft as a brush, but very very ravenous); you can wave your towel in emergencies as a distress signal, and of course you can dry yourself off with it if it still seems to be clean enough.</p> <p>More importantly, a towel has immense psychological value. For some reason, if a strag (strag: nonhitchhiker) discovers that a hitchhiker has his towel with him, he will automatically assume that he is also in possession of a toothbrush, washcloth, soap, tin of biscuits, flask, compass, map, ball of string, gnat spray, wet-weather gear, space suit etc., etc. Furthermore, the strag will then happily lend the hitchhiker any of these or a dozen other items that the hitchhiker might accidentally have “lost.” What the strag will think is that any man who can hitch the length and breadth of the Galaxy, rough it, slum it, struggle against terrible odds, win through and still knows where his towel is, is clearly a man to be reckoned with.</p> <p>Hence a phrase which has passed into hitch hiking slang, as in “Hey, you sass that hoopy Ford Prefect? There’s a frood who really knows where his towel is.”</p> </blockquote> <h4 id="more">more</h4> <ul> <li>passport</li> <li>document for your health insurance in the US</li> <li>smartphone</li> <li>camera - I bought the <a href="//martin-thoma.com/panasonic-lumix-tz41/">Panasonic Lumix DMC-TZ41</a> for 260 Euro and 64 GB Flash storage for 32 Euro for this trip. It is worth the money! It is an exceptional camera!</li> <li>laptop</li> <li>chargers</li> <li>power adapters (at least 2!). I can recommend this <a href="http://www.amazon.de/gp/product/B003UUAE76/ref=oh_aui_detailpage_o09_s00?ie=UTF8&amp;psc=1">big adapter</a>. Don’t take the small ones! They are very loose.</li> <li>hygiene products (toothbrush, dental floss, dental floss, razor, shaving foam)</li> </ul> <h2 id="overview-by-time">Overview by time</h2> <p>On 10.01.2014 I decided that I would like to go to the US. At 26.04.2014 I got my passport with the visa back. So it took more than 4 months until I could finally be sure that I can go to the US. Keep that in mind!</p> <p>I have written down when I did what (that sounds soo wrong - please correct me if you know how to express that in English). It should help you to plan your trip.</p> <h3 id="application">Application</h3> <p>A first step is the application as described <a href="http://interact.anthropomatik.kit.edu/120.php">here</a>. A general contact person is <a href="http://isl.anthropomatik.kit.edu/english/21_94.php">Margit Rödder</a>.</p> <h3 id="get-all-required-documents-to-oie">Get all required documents to OIE</h3> <p>After you’ve got accepted by the interACT advisory board (whoever that is), you have to get a ‘bank statement’. These are some lines where your bank confirms that you have enough money to live from when you’re in the US. It is very important that this statement is in English. So you should have about 1775 US-Dollar per month on your bank account. This means, if you want to be in the US for 4 months, make sure that you have at least 7100 US-Dollar on your account</p> <ul> <li>For customers of ‘Sparkasse’ this costs 25 Euro and you have to make sure that what you get is in English.</li> <li>For customers of ‘comdirect’ this costs 10 Euro</li> <li>For customers of ‘Volksbank / Raiffeisenbank’ this seems to be free.</li> </ul> <p>So I gave the bank statement and a copy of my passport to Margit Rödder.</p> <p>Some days later I’ve received an invitation from my advisor at CMU and some legal stuff I had to sign. I did this and send a copy to Faith Bold.</p> <p><strong>26.03.2014</strong> All documents are signed and I sent them to Faith.</p> <p><strong>26.03.2014</strong> Faith submitted the documents to the OIE.</p> <h3 id="receive-documents-from-oie">Receive documents from OIE</h3> <p><strong>03.04.2014</strong>: Got e-mail from UPS that they got my forms. Nice to know.</p> <p><strong>07.04.2014</strong>: I’ve got my forms now (especially DS-2019). It seems as if I have to pay a fee of 180 US-Dollar for SEVIS. There is no refunding possible when I don’t get the visa (<a href="http://web.mit.edu/scholars/intlscholars/visas/sevisfee.html#refund">source</a>). And that’s not the same as the visa application fee (which is additional 160.00 US-Dollar).</p> <p>So I’ve paid the SEVIS fee on <a href="https://www.fmjfee.com">www.FMJfee.com</a>. You need one of the following credit cards for that step:</p> <ul> <li>American Express</li> <li>Diners Club</li> <li>Discover</li> <li>MasterCard</li> <li>Visa</li> </ul> <h3 id="ds-160">DS-160</h3> <p><strong>14.04.2014</strong>: I’ve filled this form.</p> <ul> <li>Address: You can fill in the address of your department (see admission document header)</li> <li><a href="https://vimeo.com/vpu/review/87266687/042159e141">Know your rights video</a> and <a href="http://travel.state.gov/content/visas/english/general/rights-protections-temporaty-workers.html">information</a></li> </ul> <h3 id="visa-and-visiting-the-us-embassy">Visa and Visiting the U.S. embassy</h3> <p>You have to <a href="http://www.ustraveldocs.com/de/de-niv-paymentinfo.asp">pay here</a> for your visa. Some hints:</p> <ul> <li>Your exchange number usually starts with a P</li> <li>SEVIS number is on top of DS-2019 (N….)</li> </ul> <p>Some first information: <a href="http://german.germany.usembassy.gov/visa/niv/visakategorien/j/">link</a></p> <p>There is quite a lot of stuff you may not bring to the embassy (<a href="http://photos.state.gov/libraries/frankfurt/9318/consular_pdf/Security%20Notice%20for%20Consular%20Customers%20German.pdf">list</a>)</p> <p>You can see <a href="http://travel.state.gov/content/visas/english/general/wait-times.html/">visa wait times</a> online. I had to go to Frankfurt and that were about 2 days.</p> <p>You do not need a DS-7002, because that’s only for interns. You’re a short-term scholar.</p> <p>See also: <a href="http://www.path2usa.com/visitor-visa-guide/visa-interview">Visa interview information</a></p> <p>Check this checklist: <a href="http://germany.usembassy.gov/visa/nonimmigrant/documents/">USembassy.gov nonimmigrant documents</a></p> <p><strong>23.04.2014</strong></p> <ul> <li>08:20: Although my appointment was scheduled for 9 o’clock, I’ve been there much earlier. There was a ~20m queue with ~80 people waiting.</li> <li>08:59: I arrived at the first counter window. This one is outside of the embassy. I had to show my documents, tell the officer which visa I’m going to apply for. He gave me a “service ticket”. With that ticket I could queue into the “security check” queue. That one is also outside of the embassy. I had to remove my belt and my wallet, put it into a plastic bag that I was given. After that, I could enter. Then I put my jacket and the plastic bag into a box that got through a scanner.</li> <li>09:05: Next I got to a “welcome desk”. A lady gave me a sheet of paper and told me to arrange the documents listed (and only those documents) there in the right order. It was something like: passport, SEVIS confirmation, photo, DS-160, DS-2019.</li> <li>09:07: Line up in the next queue *sigh*.</li> <li>09:30: I gave the officer my documents, she returned the photograph to me (seems as if this is not necessary if you’ve already uploaded it) and scanned my fingers.</li> <li>09:35: Line up in the next queue…</li> <li>09:40: Scan my fingers … again.</li> <li>09:45: Line up in the final queue past the “T” sign.</li> <li>09:55: This is the first officer that asked my some questions. The questions were: * Officer: Where do you want to go and what do you want to do there? * Me: I want to go to CMU, Carnegie Mellon University in Pittsburgh, Pennsylvania, to write my bachelors thesis in computer science. * Officer: Who will pay for your expenses? * Me: I have a scholarship called “interACT” and I pay the rest by myself. * Officer: Your visa has been approved. You will receive your passport within one week.</li> </ul> <p>That was it.</p> <h3 id="after-visa-stuff">After-VISA-Stuff</h3> <p><strong>26.04.2014</strong></p> <p>My passport arrived with the visa in it. Now I’ve contacted about 20 people I found on craigslist asking for a room in Pittsburgh.</p> <p><strong>27.04.2014</strong></p> <p>Finding a room to live fro 3 months in Pittsburgh is more difficult than I thought.</p> <p>And finding a room to store my stuff for those 3 months in Karlsruhe is also not so easy. All self-storage services like <a href="http://www.lager7.eu/">lager7</a>, <a href="http://www.lagerbox.com/">lagerbox.com</a> and <a href="http://www.deinlagerplatz.de/">deinlagerplatz.de</a> are not in Karlsruhe. But I thought finding a cellar / garage near Karlsruhe for 50 Euro / month or less would be easy …</p> <p>edit: I finally decided to store most of my stuff at my fathers and sublease the room. That was a good decision. Here are some documents for subleasing. But before you start ask your landlord if you’re allowed to sublease!</p> <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/zwischenmiete-vertrag">Zwischenmietvertrag</a></li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/confirmation-zwischenmiete">Bestätigung Schlüsselübergabe</a></li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/confirmation-zwischenmiete-re">Bestätigung Schlüsselübergabe (zurück)</a></li> </ul> <p><strong>07.05.2014</strong></p> <p>An e-mail arrived from “Baden-Württemberg-Stipendium” telling me that I now have full access to their material and that I have to sign something and sent it back to them.</p> <p>They also told me that my scholarship is 900 Euro / month for 4 months. Finally some good news! Eventually it will not get as expensive as I thought!</p> <h3 id="getting-the-flight-tickets">Getting the flight tickets</h3> <p>I have heard that fluege.de has a very bad service. They seem not to send you the tickets in time (I’ve heard something about two weeks later!) and they don’t show the correct price. There is more information on <a href="https://de.wikipedia.org/wiki/Fluege.de#Ermittlungen">Wikipedia.de</a>.</p> <p><a href="http://www.onetwotrip.com/">OneTwoTrip</a> on the other hand had some good reviews <a href="http://www.presseportal.de/pm/107111/2452487/branchenneuling-onetwotrip-ueberzeugt-bei-portaltest-mit-benutzerfreundlichen-suchfunktionen-und">1</a> <a href="http://www.testberichte.de/p/onetwotrip-de-tests/flug-portal-testbericht.html">2</a>.</p> <p>Here is a (German) explanation of the booking process:</p> <iframe width="512" height="288" src="//www.youtube.com/embed/-rv5rG3hUFw" frameborder="0" allowfullscreen=""></iframe> <p>Other online portals are:</p> <ul> <li><a href="http://www.skyscanner.de/">skyscanner.de</a> has only one rating on <a href="http://www.ciao.de/SkyScanner_net__2573834">ciao.de</a></li> <li><a href="http://www.swoodoo.com/">swoodoo.com</a> is a meta search engine that uses fluege.de</li> <li><a href="http://www.billigflieger.de/">billigflieger.de</a> has only 3 ratings on <a href="http://www.ciao.de/billigflieger_de__1072783">ciao.de</a> and 60 on <a href="http://www.trustpilot.de/review/www.billigfluege.de">trustpilot.de</a></li> <li><a href="http://www.expedia.de/">expedia.de</a> has 3/5 stars on <a href="http://www.ciao.de/Expedia_de__56035">ciao.de</a> and 1/5 stars on <a href="http://www.trustpilot.de/review/www.expedia.de">trustpilot.de</a></li> <li><a href="http://fluege.de">fluege.de</a> has 2.5/5 stars on <a href="http://www.ciao.de/fluege_de__8290748">ciao.de</a> and 3/5 stars on <a href="http://www.trustpilot.de/review/fluege.de">trustpilot.de</a></li> <li><a href="http://www.cheaptickets.de/">cheaptickets.de</a> has very bad critics on <a href="https://de.wikipedia.org/wiki/CheapTickets">Wikipedia</a> (see <a href="http://www.ciao.de/Cheaptickets_de__7766724">ciao.de</a>) but 4/5 stars on <a href="http://www.trustpilot.de/review/www.cheaptickets.de">trustpilot.de</a></li> </ul> <p>Baggage: <a href="https://www.united.com/web/en-US/content/travel/baggage/default.aspx">united.com</a></p> <p><strong>IMPORTANT</strong> If possible, try not to fly over Chicago! That Airport is HUGE. I had 1.5 hours to get my next flight and I did not manage it. It took me quite a while to realize that you have to get into a train to get to the other terminal. And you have to re-checkin your luggage. That’s annoying! (I did not have to do that when I left the US)</p> <h3 id="preparing-and-flight">Preparing and flight</h3> <p><strong>28.05.2014</strong>: I’ve transferred the money for the flat. All of it.</p> <p><strong>30.05.2014</strong>: I’ve went to the German airport in Munich about 2 hours earlier to make sure that I don’t miss my flight. We arrived at the correct terminal. First of all, I had to “give up” (is it called “check-in”?) my luggage. After that, I spend some time with my father.</p> <p>Then, 10 minutes before the “Board time” began, I went through the security checkpoint. I had to put my backpack into a plastic box, my large electronic devices into separate ones (because the metal / electronic blocks the rays) and my belt in another one. Make sure you don’t have anything in your pockets.</p> <p>After that, you can go through a metal detector. You get checked with a hand held device after that.</p> <p>Next, you have to find your “gate”. This is the place where you go onto the plane.</p> <p>As soon as I arrived at the correct airport I had to find my luggage. You have to know that there are signs e.g. “Luggage A-M”. Those letters “A-M” refer to the airline (in my case United), not to your name!</p> <p>The next step was to get from airport to the house. As I arrived after 12p.m. I had to go by taxi which cost. Remember: You should give a tip of at least 10%, but rather 15%.</p> <p>Getting into the house was the next step to take. I was really lucky that a neighbor was on the terrace and gave me her phone to call my friend who lives in that house.</p> <h3 id="first-impressions">First impressions</h3> <p><strong>01.06.2014</strong>: We visited a some stores and <a href="https://en.wikipedia.org/wiki/Dave_and_Buster%27s">Dave and Buster’s</a> which is a video arcade.</p> <p><strong>02.06.2014</strong>: I’ve got to know Jae Cho who now has the job that Faith had before. She introduced me to everybody. After that, I was sent to Jill Lentz. She is in GHC which is short for “Gates Hillman Center”. “Gates” and “Hillman” are two buildings that are connected. Jill gave me a form from “TheHUB” which is a student service center.</p> <p>I’ve just ordered a sim card at <a href="http://ultra.me">ultra.me</a></p> <h3 id="trip-to-new-york">Trip to New York</h3> <p><strong>11.06.2014</strong>: 50.15 Euro for the bus tickets and 94.42 Euro for the hotel.</p> <p>We (Emanuel, David, Damir and me) went to New York by bus. That took quite a while, but it was quite cheap and the bus was comfortable. Not like some of the remote buses in Germany where you don’t have any place for yourself.</p> <p>The <a href="http://www.royalparkhotelnyc.com/">Royal Park Hotel</a> is very central and very cheap, but I would not recommend it. The smell was disgusting (probably from bug spray?), we had a power blackout once (eventually because 4 people wanted to charge their phones, a laptop, two tables and a camera simultaneously in one room?) and the shower was shared with other rooms.</p> <p>I recommend to visit the central park. It is great!</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Central-Park-08.jpg" class="image"><img src="//martin-thoma.com/captions/Central-Park-08.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Central-Park-15.jpg" class="image"><img src="//martin-thoma.com/captions/Central-Park-15.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Central-Park-12.jpg" class="image"><img src="//martin-thoma.com/captions/Central-Park-12.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Central-Park-18.jpg" class="image"><img src="//martin-thoma.com/captions/Central-Park-18.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Squirrel-5.jpg" class="image"><img src="//martin-thoma.com/captions/Squirrel-5.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Echinacea-purpurea-macro.jpg" class="image"><img src="//martin-thoma.com/captions/Echinacea-purpurea-macro.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <p>The <a href="http://www.amnh.org/">American Museum of Natural History</a> is ok. You can see something about science and astronomy in the basement and around the Hayden Sphere, but not much. The rest is about stones, people, plants and animals in America. I don’t think that mammals are very interesting, so that was pretty boring for me.</p> <p>It has some “Special Exhibitions” for which you have to pay in advance if you want to be able to see them. The “Dark Universe” special exhibition is probably not worth the money if you have been to a planetarium before. I have seen very similar shows in Augsburg and the movie did not contain information that was new to me.</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Smoky-quartz.jpg" class="image"><img src="//martin-thoma.com/captions/Smoky-quartz.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Smoky Quartz</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Wulfenite.jpg" class="image"><img src="//martin-thoma.com/captions/Wulfenite.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Wulfenite</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Hayden-sphere-panorama.jpg" class="image"><img src="//martin-thoma.com/captions/Hayden-sphere-panorama.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Hayden sphere</div></div></li></ul> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Labradorite-2.jpg" class="image"><img src="//martin-thoma.com/captions/Labradorite-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Labradorite</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Muscovite-crystal-structure-showing-cleavage.jpg" class="image"><img src="//martin-thoma.com/captions/Muscovite-crystal-structure-showing-cleavage.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Muscovite crystal structure showing cleavage</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Rosenhof-green-frog-dissection.jpg" class="image"><img src="//martin-thoma.com/captions/Rosenhof-green-frog-dissection.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Rosenhof: Green frog dissection</div></div></li></ul> <p>There are more images from my trip to New York City on <a href="https://commons.wikimedia.org/wiki/Category:Images_by_Martin_Thoma/NY">Wikipedia Commons</a>.</p> <p>Brooklyn Bridge is also interesting. You can take some nice pictures there at night:</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Brooklyn-Bridge-02.jpg" class="image"><img src="//martin-thoma.com/captions/Brooklyn-Bridge-02.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Brooklyn-Bridge-03.jpg" class="image"><img src="//martin-thoma.com/captions/Brooklyn-Bridge-03.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Brooklyn-Bridge-06.jpg" class="image"><img src="//martin-thoma.com/captions/Brooklyn-Bridge-06.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Brooklyn-Bridge-09.jpg" class="image"><img src="//martin-thoma.com/captions/Brooklyn-Bridge-09.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Brooklyn-Bridge-18.jpg" class="image"><img src="//martin-thoma.com/captions/Brooklyn-Bridge-18.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Brooklyn-Bridge-22.jpg" class="image"><img src="//martin-thoma.com/captions/Brooklyn-Bridge-22.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <p>Ground Zero is also a must-see. It is very impressive. It is the biggest human build waterfall:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/09/NYC-Memorial-Pool-North-2.jpg"><img src="//martin-thoma.com/captions/NYC-Memorial-Pool-North-2.jpg" alt="Ground Zero" width="500" height="375" class="" /></a><p class="wp-caption-text">Ground Zero</p></div> <p>And - of course - liberty island and the statue of liberty. You will also get to Ellis island and the immigrant museum. That was interesting!</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Liberty-5-national-park-service-boat.jpg" class="image"><img src="//martin-thoma.com/captions/Liberty-5-national-park-service-boat.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Ellis-Island-06.jpg" class="image"><img src="//martin-thoma.com/captions/Ellis-Island-06.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/09/Liberty-Island-2.jpg" class="image"><img src="//martin-thoma.com/captions/Liberty-Island-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <h2 id="money---how-much-does-it-cost">Money - How much does it cost?</h2> <p>You have to pay quite a lot in advance. I’m my case, it were 3218.06 Euro:</p> <ul> <li><strong>bank statement</strong>: 25 Euro</li> <li><strong>SEVIS fee</strong>: 180 US-Dollar = 131.45 Euro + 1.97 Euro “ENTGELD AUSLAND”</li> <li><strong>VISA application fee</strong>: 160.00 US-Dollar = 116.70 Euro</li> <li><strong>2 photos for J1 visa</strong>: 15.00 Euro</li> <li><strong>traveling to Frankfurt for Visa application</strong>: 2.30 Euro + 6.00 Euro + 8.00 Euro = 16.30 Euro</li> <li><strong>Stay one day in Frankfurt</strong>: 59.00 Euro</li> <li><strong>passport</strong>: 37.50 Euro</li> <li><strong>health insurance</strong>: 102.72 Euro</li> <li><strong>casualty insurance</strong>: 13.44 Euro</li> <li><strong>Flight tickets</strong>: 961.62 Euro</li> <li><strong>luggage scale “Soehnle 66172”</strong>: 16.99 Euro</li> <li><strong>power adapter USA2Schuko</strong>: 4.49 Euro</li> <li><strong>rent for 3 months</strong>: 1715.88 Euro</li> </ul> <p>I arrived in the US with 2000 US-Dollar in traveler checks and 200 US-Dollar in cash.</p> <p>I payed 1451.68 Euro for the traveler checks and 151.63 Euro for the cash. My VISA-card expenses were 338.31 Euro. I had to transfer 144.57 Euro to friends who payed the trip to New York in advance. So an upper bound for my expenses for the trip to the US is</p> <p>(3218.06+1451.68+151.63+338.31+144.57) Euro = 5304.25 Euro</p> <p>I got <code>$4 \cdot 900 = 3600$</code> Euro from interACT. So in total I had to pay 1704.25 Euro by myself.</p> <p>I got back with 950 US-Dollar in traveler checks and about 50 US-Dollar in cash. So I could get about 772 Euro back.</p> <p>In the US, I kept track of some expenses. It might give you an impression how expensive things are. Here you are:</p> <ul> <li><strong>taxi from airport</strong>: 60 US-Dollar = 44.10 Euro</li> <li><strong>Food</strong> <ul> <li>3x Stack’d: 3x 10 US-Dollar = 30 US-Dollar</li> <li>Hofbräuhaus: 23 US-Dollar (for apple juice and Schweineschnitzel!)</li> <li>Crepes: 8.03 US-Dollar (for crepes with salad and water)</li> <li>Pizza: 10.5 US-Dollar (for Pizza+Cola, including 1.5 US-Dollar tip)</li> <li>UNO Pizza: 16.67 US-Dollar</li> <li>The Original Hot Dog Shop: 7.27 US-Dollar</li> </ul> </li> <li><strong>New York</strong> <ul> <li>Bus tickets: 50.15 Euro (a friend payed it)</li> <li>Subway: 30 US-Dollar</li> <li>Eating: <ul> <li>Don Giovanni: 16.40+ 3 tip = 19.40 US-Dollar</li> <li>Texas Rotisserie &amp; Grill: <ul> <li>Gyro Sandwich: 7.61 * 2 = 15.22 US-Dollar</li> <li>Water: 1.36 US-Dollar</li> </ul> </li> <li>Shake Shack: 5.17 US-Dollar, 3.27 US-Dollar</li> </ul> </li> <li>Sight seeing: <ul> <li>Statue Cruises (go to the statue of liberty): 18.00 US-Dollar</li> <li>American Museum of Natural History: 22.00 US-Dollar</li> <li>International Center of Photography: 10.00 US-Dollar</li> <li>Phantom of the Opera: 48.57 Euro</li> </ul> </li> </ul> </li> <li><strong>miscellaneous</strong> <ul> <li>Post stamps “Global Forever”: 6.90 US-Dollar</li> <li>Spider Killer spray and water: 3.95 US-Dollar</li> <li>GetGo: Water, 24Pack: 3.99 US-Dollar</li> <li>public transportation: 20 US-Dollar in total for my complete stay in Pittsburgh</li> <li>Cinema (Let’s be Cops, 16.08.2014): 10.25 US-Dollar</li> </ul> </li> </ul> <h2 id="cmu-stuff">CMU stuff</h2> <p>When you come here, you can choose an AndrewID. This can be anything (letters).</p> <ul> <li><a href="http://www.cmu.edu/computing/network/connect/wireless/linux.html">WLAN Linux</a> with “AddTrust External CA Root”</li> </ul> <h2 id="terms">Terms</h2> <ul> <li><a href="http://www.nafsa.org/_/file/_/amresource/22cfr62.htm">22 C.F.R. Part 62</a>: A law regulating J1 visa.</li> <li>ACH: Automated Clearing House, an electronic banking network often used for direct deposit and electronic bill payment</li> <li>DS-2019: a form you need to apply for J-1 visa</li> <li>GHC: Gates Hillman Center, a building</li> <li><a href="https://en.wikipedia.org/wiki/J-1_visa">J-1 visa</a>: non-immigrant visa issued by the United States to exchange visitors participating in programs that promote cultural exchange, especially to obtain medical or business training within the U.S.</li> <li>OIE: Office of International Education</li> <li>SEVIS: <a href="https://en.wikipedia.org/wiki/Student_and_Exchange_Visitor_Program">Student and Exchange Visitor Program</a> (a program within U.S. Immigration and Customs Enforcement which monitors students and exchange visitors in the United States with F, M, or J visas status.)</li> <li>USCIS: <a href="https://en.wikipedia.org/wiki/United_States_Citizenship_and_Immigration_Services">United States Citizenship and Immigration Services</a> - a component of the United States Department of Homeland Security</li> <li>MRV - Machine Readable Visa</li> </ul> <h2 id="resources">Resources</h2> <ul> <li><a href="http://interact.anthropomatik.kit.edu">interact.anthropomatik.kit.edu</a>: Official interACT website</li> <li><a href="http://cmu.edu/oie">cmu.edu/oie</a> <ul> <li><a href="http://www.studentaffairs.cmu.edu/oie/settlinginguides/preparing.html">Settling in Guide</a> - very helpful!</li> </ul> </li> <li>StackExchange: <ul> <li><a href="http://money.stackexchange.com/q/29779/2731">What do the numbers on my VISA card mean?</a></li> <li><a href="http://english.stackexchange.com/q/162105/9880">What is a “travel validation”?</a></li> <li><a href="http://english.stackexchange.com/q/164992/9880">How do you address people at the beginning of a conversation?</a></li> <li><a href="http://travel.stackexchange.com/q/26551/13107">Can I buy a sim card for prepaid internet for the USA in Germany?</a></li> <li><a href="http://superuser.com/q/747265/64857">In how far is the Ampere number important for USB powered devices?</a></li> </ul> <p>http://nutmeggle.wordpress.com/2013/06/23/the-welcome-pack-and-the-visa/</p> </li> </ul> One-on-One Tutoring //martin-thoma.com/one-to-one-tutoring/ Wed, 10 Sep 2014 10:03:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/one-to-one-tutoring <p>I have heard that the famous universities in England have One-on-One tutoring. <small>I’m not sure if that is actually the case, but that doesn’t matter for the idea I want to explain.</small> That means one tutor helps one student only. That must be incredibly effective for learning. From my experience as a tutor and as a “coach” (Nachhilfelehrer) I know that there is a huge difference in One-on-One tutoring compared to One-on-Many tutoring, where one tutor teaches about 30 students. If you only have one student, you can focus on the needs of this single student. And I guess that the student will also be encouraged a bit more to participate. If you only have one student, the student will not sleep while you teach him. He has to stay focused, because you will notice when he doesn’t.</p> <p>So One-on-One tutoring is something we want to get.</p> <h2 id="the-problem-of-one-on-one-tutoring">The problem of One-on-One tutoring</h2> <p>It is expensive, if it would be done like tutoring is currently done. In fact I think it would be impossible, because you would not find that many tutors. However, I think there are other ways to motivate students that have already passed the exam to be a tutor for another student.</p> <h2 id="how-to-get-one-on-one-tutoring">How to get One-on-One tutoring</h2> <p>Give One-on-One tutors the possibility to write the exam again and improve their grade.</p> <p>I could imagine it to work like this: A student passes the exam, but he does not have the grade he wants. As he has already passed the exam, he will not be allowed to simply write it again. So he has to search a student who hasn’t already passed the exam and help this student to prepare for the exam. Now we have to check if the One-on-One tutor really helped the new student. I could imagine two ways that could also be combined.</p> <h3 id="one-on-one-tutoring-way-1">One-on-One tutoring: Way 1</h3> <p>The One-on-One tutor has to help the new student with the exercises. So the One-on-Many tutor gets the information which exercises were done by the One-on-One tutor and the new student. In contrast to now, not only one student would exercise, but two. In order to make sure that there is an improvement, one could increase the necessary number of points for the One-on-One tutor to a threshold of <code>$\theta_1$</code>. <code>$\theta_1$</code> should denote how much more points the student needs (in percent of the points the students need) to get the possibility to re-do the exam.</p> <p><code>$\theta_1 = 0$</code> would mean that the tutor does only need a student who gets the minimum number of points to pass the exam.</p> <p><code>$\theta_1 = 1$</code> would mean that the tutor needs his students to get double the number of points in the exercises than what he would need to be allowed to participate in the exam.</p> <p>This means <code>$\theta_1 \in [0, 1]$</code>.</p> <p><code>$\theta_1$</code> should not be zero, because that would mean that 1-on-1 tutors could choose their students right before the exam. But I want them to choose the student at the beginning of the semester. And <code>$\theta_1$</code> may not be too high. The higher it gets, the more difficult and time intensive it gets for the student and the tutor. I think the time right before an exam is the time where students learn most. If a student doesn’t achieve the <code>$\theta_1$</code> threshold, then the tutor will not have any incentive to help the student to prepare for the exam except for money or friendship. This is a good incentive for the student to keep working on excercises, even if he already got enough points to be allowed to write the exam.</p> <h3 id="one-on-one-tutoring-way-2">One-on-One tutoring: Way 2</h3> <p>The other possibility would be to enforce a minimum grade for the tutored student. So the One-on-One tutor cannot participate in the same exam as his student, but in the exam after that. And the tutor can only participate in that exam if his student got a minimum grade <code>$\theta_2$</code>, e.g. 2.3 or better.</p> <p><code>$\theta_2 = 5$</code> would mean that the student only has to participate in the exam (at KIT every student gets at least a grade of 5. The best grade is 1.0.).</p> <p><code>$\theta_2 = 1$</code> would mean that the student has to pass with the best grade so that the tutor is allowed to participate in the exam.</p> <p>Alternatively one could make that dependent on the number of students who got the grade. So <code>$\theta_2 = 10\%$</code> would mean that you choose the grade threshold in a way that makes sure that at least 10% of all students pass that requirement.</p> <p>This means <code>$\theta_2 \in [1, 5]$</code> or <code>$\theta_2 \in (0\%, 100\%]$</code>.</p> <p><code>$\theta_2$</code> should not be too bad (near 5), because then it will be too easy for many students to get another try for the exam. That would also not help the students, because the tutor would not have an incentive that is strong enough to increase the abilities of his student. However, if <code>$\theta_2$</code> gets too low (near 1.0) then most students will not try to be a tutor because it is too difficult to get a student to achieve that good results.</p> <h2 id="how-to-speak-about-it">How to speak about it</h2> <p>I would like to call this model MOOT (Martins One-on-One Tutoring model ☺ ). It is parameterized with two variables, <code>$\theta_1$</code> and <code>$\theta_2$</code>.</p> <p>I think <code>$MOOT(\theta_1=0.2, \theta_2=25\%)$</code> would be a good possibility to encourage students to help other students effectively. <code>$\theta_1$</code> is low enough to make it fairly easy for somebody who already passed the exam to “lift” a student to pass the requirement.</p> <p>So I guess <code>$MOOT(0.2, 25\%)$</code> would be a good choice. You could still argue that the tutor could simply write the excercises himself. But I don’t think that would be a problem, because then the tutor would do the excercises. He would still practice. We only get a problem if larger groups of students copy excercises. I don’t think that is the case, but I judge from the students I know. I might have a biased view on the problem.</p> <h2 id="conclusion">Conclusion</h2> <p>The two ways I proposed would in general lead to better students, remove stress from students because a single bad exam would not be that bad any more and very likely lead to better students. Students would be better on the paper (because the tutor should only be able to improve himself by the new exam and also his student should be able to achieve better results in the exam) and in the real world. Students would get an incentive to repeat what they did not understand before. They would get an incentive to help other students. For free. And it would not be that much more work for the university. I think it is easier to correct exams of good students and only a few would really take this possibility as it is really time intensive for the One-on-One tutor. But for some exams and some students that might be worth the effort.</p> <p>What do you think about it? Do you think we could introduce that model at KIT? Who could propose it? To whom should it be proposed?</p> <h2 id="other-incentives">Other incentives</h2> <p>If writing the exam again is not an option, we could try to find other incentives for tutors:</p> <ul> <li>Getting “exclusive” rights: <ul> <li>Visiting CERN or something similar</li> <li>Getting access to equipment of the university (executing your personal projects on KIT clusters, getting access to microscopes, being allowed to use lecture halls)</li> </ul> </li> <li>“Proud” of the unversity: If we could make KIT students being proud of being a student at KIT the students themselves could want to support fellow students.</li> </ul> <p>I am not sure if there is any incentive which is strong enough to support another student for one semester. Do you have an idea? Please share it in the comments!</p> The Twiddle Algorithm //martin-thoma.com/twiddle/ Sat, 06 Sep 2014 13:49:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/twiddle <p>Twiddle is an algorithm that tries to find a good choice of parameters <code>$p$</code> for an algorithm <code>$\mathcal{A}$</code> that returns an error.</p> <p>The algorithm is quite simple to implement. I guess gradient descent might be better for most cases, but Twiddle does not require any knowledge about the algorithm <code>$\mathcal{A}$</code> which might be a big advantage. And you don’t have to calculate the gradient of high dimensional functions, which is nice, too.</p> <h2 id="the-algorithm">The algorithm</h2> <p>Here is some pythonic pseudo code. <code>A</code> is an algorithm that returns an error.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777"># Choose an initialization parameter vector</span> p = [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>] <span style="color:#777"># Define potential changes</span> dp = [<span style="color:#00D">1</span>, <span style="color:#00D">1</span>, <span style="color:#00D">1</span>] <span style="color:#777"># Calculate the error</span> best_err = A(p) threshold = <span style="color:#60E">0.001</span> <span style="color:#080;font-weight:bold">while</span> <span style="color:#369;font-weight:bold">sum</span>(dp) &gt; threshold: <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(p)): p[i] += dp[i] err = A(p) <span style="color:#080;font-weight:bold">if</span> err &lt; best_err: <span style="color:#777"># There was some improvement</span> best_err = err dp[i] *= <span style="color:#60E">1.1</span> <span style="color:#080;font-weight:bold">else</span>: <span style="color:#777"># There was no improvement</span> p[i] -= <span style="color:#00D">2</span>*dp[i] <span style="color:#777"># Go into the other direction</span> err = A(p) <span style="color:#080;font-weight:bold">if</span> err &lt; best_err: <span style="color:#777"># There was an improvement</span> best_err = err dp[i] *= <span style="color:#60E">1.05</span> <span style="color:#080;font-weight:bold">else</span> <span style="color:#777"># There was no improvement</span> p[i] += dp[i] <span style="color:#777"># As there was no improvement, the step size in either</span> <span style="color:#777"># direction, the step size might simply be too big.</span> dp[i] *= <span style="color:#60E">0.95</span> </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li><a href="https://www.youtube.com/watch?v=2uQ2BSzDvXs">Twiddle - CS373 Unit 5 - Udacity</a>: Explanation of Twiddle by Sebastian Thrun</li> <li><a href="http://www.htw-mechlab.de/index.php/numerische-optimierung-in-matlab-mit-twiddle-algorithmus/">Numerische Optimierung in Matlab mit Twiddle-Algorithmus</a> (German)</li> <li><a href="http://forums.udacity.com/questions/1023236/twiddle-vs-gradient-descent">twiddle vs gradient descent</a></li> </ul> Hyperlapse //martin-thoma.com/hyperlapse/ Wed, 03 Sep 2014 04:31:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/hyperlapse <p><a href="http://research.microsoft.com/en-us/people/kopf/">Johannes Kopf</a>, a researcher at Microsoft, has recently published a stunning video about a software project he seems to have participated in. The video is about the automatic creation of hyperlapse videos:</p> <iframe width="512" height="288" src="//www.youtube.com/embed/sA4Za3Hv6ng" frameborder="0" allowfullscreen=""></iframe> <blockquote> <p>We present a method for converting first-person videos, for example, captured with a helmet camera during activities such as rock climbing or bicycling, into hyperlapse videos: time-lapse videos with a smoothly moving camera.</p> </blockquote> <p>So we are now only speaking about first-person videos. As videos created by a helmet camera might be very long and (as he accurately described it) “dead boring”, you want to speed that up. A timelaps would be a subsampling to every n-th frame. Those might be very shaky and hard to watch. That means you would at least want some image stabilization.</p> <h2 id="microsoft-hyperlapse">Microsoft Hyperlapse</h2> <p>But the software they created does more. Much more.</p> <h3 id="reconstruction">Reconstruction</h3> <p>First, it reconstructs the geometry of the captured environment. That alone is absolutely awesome. They apply a group of techniques called <a href="https://en.wikipedia.org/wiki/Structure_from_motion">structure from motion</a>.</p> <h3 id="path-planning">Path planning</h3> <p>Then they plan the path of the camera. This is a 6-dimensional problem for every point in time where you want to get an image. The 6 dimensions are:</p> <ul> <li>(x, y, z): Position of the camera</li> <li>roll: horizontal, vertical angle</li> <li>pitch: up, down view angle</li> <li>yaw: left, right view angle</li> </ul> <p>In case you have a problem with imagining roll, pitch and yaw you should take a look at the following image:</p> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2014/09/Flight_dynamics_with_text.png"><img src="../images/2014/09/Flight_dynamics_with_text.png" alt="Roll, pitch and yaw&lt;br/&gt;By ZeroOne" width="" height="" class="" /></a><p class="wp-caption-text">Roll, pitch and yaw<br />By [ZeroOne](https://commons.wikimedia.org/wiki/File:Flight_dynamics_with_text.png)</p></div> <p>The chosen path should meet several criteria:</p> <ul> <li>It should be smooth in space</li> <li>Every path position should be close to input positions</li> <li>The path should be short</li> <li>Rotation should be smooth (that is what makes videos “shaky”)</li> <li>The rendering quality should be as high as possible</li> </ul> <p>The first 3 steps were achived by spline fitting.</p> <h3 id="rendering">Rendering</h3> <p>That step combines several output frames to render the desired camera image.</p> <h2 id="nice-timelapses">Nice timelapses</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/8dTzy_N0Pn4" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="288" src="//www.youtube.com/embed/fSj73DuFD9I" frameborder="0" allowfullscreen=""></iframe> Mouse clicking games //martin-thoma.com/mouse-clicking-games/ Sat, 23 Aug 2014 14:15:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/mouse-clicking-games <p>Do you know games like <a href="http://orteil.dashnet.org/cookieclicker/">cookie clicker</a> where you only have to click a lot?</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/08/cookie-cliker.png"><img src="//martin-thoma.com/captions/cookie-cliker.png" alt="Cookie Clicker" width="500" height="253" class="" /></a><p class="wp-caption-text">Cookie Clicker</p></div> <p>You can do that automatically with the following Python script.</p> <p>Just execute <code>xdotool getmouselocation --shell</code> before that to find the position of your mouse.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Tool to make automatic clicks VERY fast (useful for idle games).</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">time</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">random</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">main</span>(clicks, twiggle, x, y, delay): <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(clicks): xrand = random.randint(-twiggle, twiggle) yrand = random.randint(-twiggle, twiggle) xpos, ypos = x+xrand, y+yrand os.system(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">xdotool mousemove %i %i click 1</span><span style="color:#710">&quot;</span></span> % (xpos, ypos)) <span style="color:#080;font-weight:bold">if</span> delay &gt; <span style="color:#00D">0</span>: time.sleep(delay) <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span> parser = ArgumentParser() <span style="color:#777"># Add more options if you like</span> parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-c</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--clicks</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">clicks</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">number of clicks that will be done</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">500</span>, type=<span style="color:#369;font-weight:bold">int</span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-t</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--twiggle</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">twiggle</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">how much should the cursor move randomly</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">50</span>, type=<span style="color:#369;font-weight:bold">int</span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-x</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x coordinate where to click</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">711</span>, type=<span style="color:#369;font-weight:bold">int</span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-y</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y coordinate where to click</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">467</span>, type=<span style="color:#369;font-weight:bold">int</span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--delay</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">delay</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">delay between clicks</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#60E">0.01</span>, type=<span style="color:#369;font-weight:bold">float</span>) args = parser.parse_args() main(args.clicks, args.twiggle, args.x, args.y, args.delay) </pre></div> </div> </div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/08/cookie-clicker-5min.png"><img src="//martin-thoma.com/captions/cookie-clicker-5min.png" alt="Cookie Clicker after 5 minutes with a script" width="500" height="252" class="" /></a><p class="wp-caption-text">Cookie Clicker after 5 minutes with a script</p></div> <p>Have fun playing those games now!</p> Citizen Science Projects //martin-thoma.com/citizen-science-projects/ Thu, 21 Aug 2014 13:27:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/citizen-science-projects <p>“Citizen Science Projects” are research projects that crowdsource a part of the research work. The idea behind that is quite simple: Some tasks of researchers are very simple. Everybody can do them.</p> <p>I think some of them are a great example of <a href="https://en.wikipedia.org/wiki/Gamification">Gamification</a>.</p> <h2 id="galaxy-zoo">Galaxy Zoo</h2> <p><a href="https://en.wikipedia.org/wiki/Galaxy_Zoo">Galaxy Zoo</a> is a crowdsourced astronomy project which invites people to assist in the classification of galaxies.</p> <p>You get some images of Galaxies and you should see some characteristics by looking at them. You get about three possible answers to every question.</p> <p>It looks like that:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/08/galaxyzoo.png"><img src="//martin-thoma.com/captions/galaxyzoo.png" alt="Galaxy Zoo" width="500" height="314" class="" /></a><p class="wp-caption-text">Galaxy Zoo</p></div> <h2 id="moon-zoo">Moon Zoo</h2> <blockquote> <p>High-resolution images of the Moon’s surface provided by the Lunar Reconnaissance Orbiter are used by volunteers to create detailed crater counts, mapping the variation in age of lunar rocks.</p> </blockquote> <p>Source: <a href="https://en.wikipedia.org/wiki/Moon_Zoo#Active_projects">Wikipedia</a></p> <iframe width="512" height="377" src="http://www.youtube.com/embed/rJHfoM6kh7w" frameborder="0" allowfullscreen=""></iframe> <p>It looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/08/moonzoo.png"><img src="//martin-thoma.com/captions/moonzoo.png" alt="Moon Zoo" width="500" height="350" class="" /></a><p class="wp-caption-text">Moon Zoo</p></div> <h2 id="eterna">EteRNA</h2> <p><a href="https://en.wikipedia.org/wiki/EteRNA">EteRNA</a> is a browser based game, developed by scientists at Carnegie Mellon University and Stanford University, that engages users to solve puzzles related to the folding of RNA molecules.</p> <p>It looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/08/eterna.png"><img src="//martin-thoma.com/captions/eterna.png" alt="EteRNA" width="500" height="348" class="" /></a><p class="wp-caption-text">EteRNA</p></div> <h2 id="write-math">Write Math</h2> <p><a href="http://write-math.com">write-math.com</a> is my own project. The aim of the project is to get fast and accurate recognition of mathematical symbols. To do so, I needed data.</p> <p>Currently, the project is still under heavy development. Currently, most work I do is done offline. Hence the project might not improve until end of October (2014).</p> <p>It looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/08/write-math-front-page.png"><img src="//martin-thoma.com/captions/write-math-front-page.png" alt="write math" width="500" height="562" class="" /></a><p class="wp-caption-text">write math</p></div> <p>The most interesting part might be the <a href="http://write-math.com/render/?raw_data_id=19181">interactive preprocessing experiments</a>.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="http://eternagame.org/web/">EteRNA</a></li> <li>Galaxy Zoo: <a href="http://www.galaxyzoo.org/how_to_take_part">How to take part</a></li> <li>Moon Zoo: <a href="http://www.moonzoo.org/how_to_take_part">How to take part</a></li> </ul> GPUs - Supercomputers for your home //martin-thoma.com/gpu-supercomputers-for-your-home/ Wed, 20 Aug 2014 23:26:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/gpu-supercomputers-for-your-home <p>A few days ago I got some of my neural net code to work with a GPU. The GPU is called “Tesla C2075”. It is able to get 515 GFlops peak performance. It has 448 CUDA cores that work with 1.15 GHz and it has 6GB GDDR5 memory.</p> <p>My code needed about 10 hours to run before. After that, it only needed 10 minutes. That is 60 times faster! The library that did this miracle for me is called <a href="http://deeplearning.net/software/theano/">Theano</a>)</p> <p>Out of curiosity, I’ve searched for current high-end gamer graphic cards. I found nVidia Titan Z:</p> <iframe width="512" height="288" src="//www.youtube.com/embed/2JjxgJcXVE0" frameborder="0" allowfullscreen=""></iframe> <p>The Titan Z has 5760 CUDA cores. It can get 4061 GFLOPS x2 and has 12 GB of memory. That technological wonder-work costs only 2802 Euro.</p> <p>To put that into perspective: In 2005, you would probably have been on place 68 of the TOP500 supercomputers world wide! (<a href="http://www.top500.org/list/2005/06/?page=1">source</a>).</p> <p>Isn’t that crazy?</p> <h2 id="see-also">See also:</h2> <ul> <li><a href="http://www.geforce.com/hardware/desktop-gpus/geforce-gtx-titan-z/specifications">Titan Z Specification</a></li> <li><a href="http://superuser.com/questions/805217/what-are-the-differences-between-scientific-gpus-and-gaming-gpus">What are the differences between “scientific GPUs” and “gaming GPUs”?</a></li> </ul> MediaViewer and Superprotect //martin-thoma.com/media-viewer-and-superprotect/ Fri, 15 Aug 2014 14:35:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/media-viewer-and-superprotect <p>Recently, a heated discussion started on the German Wikipedia about Superprotect. This article should give a very short summary how it came to this discussion.</p> <h2 id="timeline">Timeline</h2> <ul> <li><strong>25. July 2014</strong>: Straw poll in the German Wiki began (<a href="https://de.wikipedia.org/wiki/Wikipedia:Meinungsbilder/Medienbetrachter">link</a>)</li> <li><strong>08. August 2014</strong>: Straw poll in the German Wiki ended. 72.5% voted for a default deactivation of the MediaViewer</li> <li><strong>09. /10. August 2014</strong>: The Admins <a href="https://de.wikipedia.org/wiki/Benutzer:DaB.">DaB.</a>, <a href="https://de.wikipedia.org/wiki/Benutzer:Raymond">Raymond</a> and <a href="https://de.wikipedia.org/wiki/Benutzer:JEissfeldt_(WMF)">JEissfeldt (WMF)</a> repeatedly change <a href="https://de.wikipedia.org/wiki/MediaWiki:Common.js">MediaWiki:Common.js</a> to activate / deactivate the MediaViewer for the German wiki</li> <li><strong>10. August 2014</strong>: Superprotect got introduced and Erik Möller (<a href="https://de.wikipedia.org/wiki/Benutzer:Eloquence">User:Eloquence</a>) protected MediaWiki:Common.js.</li> </ul> <h2 id="the-mediaviewer">The MediaViewer</h2> <p>You can <a href="https://en.wikipedia.org/wiki/Wikipedia:Media_Viewer">try the MediaViewer</a> to get a feeling what this is all about.</p> <p>You can view some images of the MediaViewer here:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/08/wikipedia-first-view.png" class="image"><img src="//martin-thoma.com/captions/wikipedia-first-view.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Article</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/08/media-viewer-first-click.png" class="image"><img src="//martin-thoma.com/captions/media-viewer-first-click.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">First click on image with MediaViewer</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/08/without-media-viewer-first-click.png" class="image"><img src="//martin-thoma.com/captions/without-media-viewer-first-click.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">First click on image without MediaViewer</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/08/media-viewer-first-click-notes.png" class="image"><img src="//martin-thoma.com/captions/media-viewer-first-click-notes.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">notes to the MediaViewer interface</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/08/media-viewer-more-information.png" class="image"><img src="//martin-thoma.com/captions/media-viewer-more-information.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">MediaViewer Bottom 'Tab'</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/08/media-viewer-use-this-file.png" class="image"><img src="//martin-thoma.com/captions/media-viewer-use-this-file.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">MediaViewer 'Use this file'</div></div></li></ul> <p>There has been a survey that suggests that 60% of all users like the MediaViewer (<a href="https://www.mediawiki.org/wiki/Multimedia/Media_Viewer/Survey">source</a>). However, there are concerns that the survey was biased (<a href="https://en.wikipedia.org/wiki/Wikipedia:Media_Viewer/June_2014_RfC#Biased_survey_wording">source</a>).</p> <p>You should know that you can easily disable the MediaViewer if you have an account:</p> <blockquote> <p>Preferences → Appearance → Files = uncheck ‘Enable Media Viewer’</p> </blockquote> <p>The question is: Should the MediaViewer be activated per default?</p> <h3 id="pro">Pro</h3> <ul> <li>Average users want to see the image in a higher resolution. The MediaViewer looks more professional than the old view.</li> </ul> <h4 id="wrong-arguments">Wrong arguments</h4> <ul> <li>The copyright notice doesn’t get in my way.<br /> It is a legal obligation to show the copyright notice.</li> </ul> <h3 id="contra">Contra</h3> <ul> <li>The MediaViewer doesn’t give new functionality: One could see high-resolution images before by simply clicking a second time on the image.</li> <li>The MediaViewer makes it more difficult for new users to edit file descriptions.</li> <li>The MediaViewer hides information like the copyright status. <ul> <li>Charts and maps that are color-coded and change/are edited over time and have a legend/key in multiple languages simply do not work with this interface. See <a href="https://en.wikipedia.org/wiki/Same-sex_marriage_in_the_United_States#mediaviewer/File:Samesex_marriage_in_USA.svg">this example</a>.</li> </ul> </li> <li>The MediaViewer makes browsing difficult on touch-screen devices that use pinch-to-zoom.</li> <li>It becomes almost unusably slow on slower machines or machines on a slow connection.</li> <li>MediaViewer makes it more difficult to find the image in the highest resolution.</li> </ul> <h4 id="wrong-arguments-1">Wrong arguments</h4> <ul> <li>It’s in the way of long-term wikipedia editors.<br /> This argument is wrong, because long-term wikipedia editors can simply disable it. They should know how to do it.</li> <li>Logged in in users don’t need this feature.<br /> Again, they can disable it.</li> </ul> <h3 id="good-comments">Good comments</h3> <ul> <li>The default setting for logged-in users should be the same as for unregistered users, so that new users have fewer surprises to deal with.</li> </ul> <h3 id="alternatives-to-default-enable-mediaviewer">Alternatives to default-enable MediaViewer</h3> <ul> <li>Change from opt-out to opt-in</li> <li>Disabled for current users and enabled for newly registered users</li> </ul> <h2 id="superprotect">Superprotect</h2> <p>The German Wikipedia community decided to disable MediaViewer per default. As the MediaViewer got rolled out, some admins in the German Wikipedia enabled / disabled it (see <a href="https://de.wikipedia.org/wiki/MediaWiki:Common.js">version history of Common.js</a>). This was the reason to create superprotect:</p> <blockquote> <p>Add a new protection level called “superprotect” <br /> Assigned to nobody by default. Requested by Erik Möller for the purposes of protecting pages such that sysop permissions are not sufficient to edit them. Change-Id: Idfa211257dbacc7623d42393257de1525ff01e9e</p> </blockquote> <p>Source: <a href="https://gerrit.wikimedia.org/r/#/c/153302/">gerrit.wikimedia.org</a></p> <p>That started another community poll in the German wiki:</p> <p><a href="https://de.wikipedia.org/wiki/Wikipedia:Umfragen/Superschutz">Wikipedia:Umfragen/Superschutz</a></p> <p>and</p> <p><a href="https://de.wikipedia.org/wiki/Wikipedia:Meinungsbilder/Benutzerrecht_Superprotect">Wikipedia:Meinungsbilder/Gruppenrecht Superschutz</a></p> <p>Now the question is: Should the new group right ‘super protect’ be kept?</p> <h3 id="pro-1">Pro</h3> <ul> <li>Super protect is a necessary tool to temporarily prevent abuse of admin powers in heated discussions.</li> <li>The WMF has the legal right to do what they want on wikipedia.org.</li> <li>The WMF controls the technical details of the Wikipedia platform, whereas the community only controls the content.</li> </ul> <h4 id="wrong-arguments-2">Wrong arguments</h4> <ul> <li>The super protect right was necessary as one admin was abusing his power.<br /> If the problem is only one admin, there already is the possibility to remove the admin status of this user.</li> <li>The WMF has the legal right to do what they want and they need superprotect to have legal security.<br /> That is simply wrong. There is (currently) no case where an admin tried to put something illegal on Wikipedia.org and abused his admin rights to keep it there.</li> </ul> <h3 id="contra-1">Contra</h3> <ul> <li>There is no need for such a tool, as the community is able to solve ‘wheel wars’.</li> <li>In case of the abuse of powers by admins, these powers can be removed (see <a href="https://en.wikipedia.org/wiki/Wikipedia:Administrators#Review_and_removal_of_adminship">Review and removal of adminship</a>)</li> <li>The community wants to organize Wikipedia by themselves without intervention from the WMF. The problem for many users seems to be that the WMF is not elected, whereas admins are (see <a href="https://en.wikipedia.org/wiki/Wikipedia:Administrators#Becoming_an_administrator">Wikipedia:Administrators#Becoming_an_administrator</a> - there seem to be differences in the English / German Wiki).</li> <li>The new concept of ‘super protection’ was introduced too fast without a concept which was discussed within the community.</li> <li>The risk of misuse of power is too high as there is no mutual control.</li> </ul> <h3 id="comments">Comments</h3> <p>I think super protect might be a good solution to temporarily freeze pages when more than two admins have a wheel war. In that case it could be implemented so that it can only freeze a page for 7 days and after those 7 days the page cannot be frozen for at least 14 days (one would have to discuss the numbers).</p> <p>This way, it can be a tool for de-escalation and the abuse can be limited.</p> <p>Also, sites that get frozen must have at least two back-and-forth edits by two admins and the community must have voted for freezing.</p> <h2 id="terms">Terms</h2> <p><strong><a href="https://en.wikipedia.org/wiki/Wikipedia">Wikipedia</a></strong> is the free Internet encyclopedia at wikipedia.org.</p> <p><strong><a href="https://en.wikipedia.org/wiki/MediaWiki">MediaWiki</a></strong> is the software that Wikipedia uses. It is also free and it gets developed by the Wikimedia Foundation and others. You can <a href="https://www.mediawiki.org/wiki/MediaWiki">download MediaWiki here</a> and find the source code via <code>https://gerrit.wikimedia.org/r/p/mediawiki/core.git</code>.</p> <p><strong><a href="https://en.wikipedia.org/wiki/Wikimedia_Foundation">Wikimedia Foundation</a></strong> (short: WMF) is an American non-profit and charitable organization headquartered in San Francisco, California, that operates wikipedia.org.</p> <p><strong><a href="https://en.wikipedia.org/wiki/Wikipedia:Media_Viewer">MediaViewer</a></strong> is a JavaScript that gives the possibility to browse through all images of an article by using a diashow.</p> <p><strong>Wheel war</strong> is happening when two or more admins repeatedly revert their changes.</p> <h2 id="sources">Sources</h2> <ul> <li><a href="https://de.wikipedia.org/wiki/Wikipedia:Superschutz">Wikipedia:Superschutz</a> (German)</li> <li><a href="https://www.mediawiki.org/wiki/Multimedia/Media_Viewer/Survey">Multimedia/Media Viewer/Survey</a></li> <li><a href="https://en.wikipedia.org/wiki/Wikipedia:Media_Viewer/June_2014_RfC">Wikipedia:Media Viewer/June 2014 RfC</a></li> <li><a href="https://de.wikipedia.org/wiki/Wikipedia:Meinungsbilder/Medienbetrachter">Wikipedia:Meinungsbilder/Medienbetrachter</a></li> </ul> Start long running processes via SSH //martin-thoma.com/start-long-running-processes-via-ssh/ Mon, 11 Aug 2014 14:51:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/start-long-running-processes-via-ssh <h2 id="screen">Screen</h2> <p><a href="https://en.wikipedia.org/wiki/GNU_Screen"><code>screen</code></a> is a nice tool that can be used to detach long running processes from the current SSH session - and be able to get it again!</p> <h3 id="basic-usage">Basic usage</h3> <p>You start it with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ screen </pre></div> </div> </div> <p>You detach it with <kbd>Ctrl</kbd> + <kbd>a</kbd> and then <kbd>d</kbd>. After you pressed this key combination, you will see</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[detached] </pre></div> </div> </div> <p>You get it back again with:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ screen -r </pre></div> </div> </div> <h3 id="named-sessions">Named sessions</h3> <p>You can start a named session with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ screen -S foo </pre></div> </div> </div> <p>and get it back with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ screen -r foo </pre></div> </div> </div> <h2 id="nohup">nohup</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ nohup command &amp; </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li><a href="http://www.tecmint.com/screen-command-examples-to-manage-linux-terminals/">10 Screen Command Examples to Manage Linux Terminals</a></li> <li><a href="http://www.mattcutts.com/blog/a-quick-tutorial-on-screen/">Matt Cutts: A quick tutorial on screen</a></li> <li><a href="http://www.gnu.org/software/screen/manual/screen.html">Screen User’s Manual</a></li> </ul> William Shatner //martin-thoma.com/william-shatner/ Wed, 06 Aug 2014 07:42:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/william-shatner <p><a href="https://en.wikipedia.org/wiki/William_Shatner">William Shatner</a> is the actor that played James Tiberius Kirk in the science fiction television series Star Trek. You can imagine how famous he is from these Twitter answers:</p> <blockquote class="twitter-tweet" lang="de"><p>.<a href="https://twitter.com/WilliamShatner">@WilliamShatner</a> Everything within normal parameters, Capt&#39;n. Robotic probe <a href="https://twitter.com/ESA_Rosetta">@ESA_Rosetta</a> arrives at comet <a href="https://twitter.com/hashtag/67P?src=hash">#67P</a> today! <a href="http://t.co/f7nuOjMVuh">http://t.co/f7nuOjMVuh</a></p>&mdash; ESA (@esa) <a href="https://twitter.com/esa/statuses/496905989548146688">6. August 2014</a></blockquote> <script async="" src="//platform.twitter.com/widgets.js" charset="utf-8"></script> <blockquote class="twitter-tweet" lang="de"><p><a href="https://twitter.com/WilliamShatner">@WilliamShatner</a> Good day, Captain. <a href="https://twitter.com/hashtag/ISS?src=hash">#ISS</a> is in standard orbit and Commander Swanson has the conn. Hope you’re having a great weekend!</p>&mdash; NASA (@NASA) <a href="https://twitter.com/NASA/statuses/495719809695621121">2. August 2014</a></blockquote> <script async="" src="//platform.twitter.com/widgets.js" charset="utf-8"></script> Logging in Python //martin-thoma.com/logging-in-python/ Fri, 01 Aug 2014 21:15:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/logging-in-python <p>Python has a nice logging module. You can use it like this:</p> <h2 id="stream-output">Stream output</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">logging</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">sys</span> logging.basicConfig(format=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">%(asctime)s %(levelname)s %(message)s</span><span style="color:#710">'</span></span>, level=logging.DEBUG, stream=sys.stdout) logging.debug(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">This message should go to the log file</span><span style="color:#710">'</span></span>) logging.info(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">So should this</span><span style="color:#710">'</span></span>) logging.warning(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">And this, too</span><span style="color:#710">'</span></span>) </pre></div> </div> </div> <h2 id="file-output">File output</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">logging</span> logging.basicConfig(filename=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">logging.log</span><span style="color:#710">'</span></span>, format=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">%(asctime)s %(levelname)s %(message)s</span><span style="color:#710">'</span></span>, level=logging.DEBUG) logging.debug(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">This message should go to the log file</span><span style="color:#710">'</span></span>) logging.info(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">So should this</span><span style="color:#710">'</span></span>) logging.warning(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">And this, too</span><span style="color:#710">'</span></span>) </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li><a href="https://docs.python.org/2/howto/logging.html">Tutorial</a></li> <li><a href="https://docs.python.org/2/library/logging.html">Documentation</a></li> </ul> Configuration files in Python //martin-thoma.com/configuration-files-in-python/ Sun, 27 Jul 2014 15:46:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/configuration-files-in-python <p>Most interesting programs need some kind of configuration:</p> <ul> <li>Content Management Systems like WordPress blogs, WikiMedia and Joomla need to store the information where the database server is (the hostname) and how to login (username and password)</li> <li>Proprietary software might need to store if the software was registered already (the serial key)</li> <li>Scientific software could store the path to BLAS libraries</li> </ul> <p>For very simple tasks you might choose to write these configuration variables directly into the source code. But this is a bad idea when you upload the code to GitHub.</p> <p>I will explain some alternatives I got to know for Python.</p> <h2 id="python-configuration-file">Python Configuration File</h2> <p>The simplest way to write configuration files is to simply write a separate file that contains Python code. You might want to call it something like <code>databaseconfig.py</code>. Then you could add the line <code>*config.py</code> to your <code>.gitignore</code> file to avoid uploading it accidentally.</p> <p>A configuration file could look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">preprocessing</span> mysql = {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">host</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">localhost</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">user</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">root</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">passwd</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">my secret password</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">db</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">write-math</span><span style="color:#710">'</span></span>} preprocessing_queue = [preprocessing.scale_and_center, preprocessing.dot_reduction, preprocessing.connect_lines] use_anonymous = <span style="color:#069">True</span> </pre></div> </div> </div> <p>Within the actual code, you can use it like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">databaseconfig</span> <span style="color:#080;font-weight:bold">as</span> cfg connect(mysql[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">host</span><span style="color:#710">'</span></span>], mysql[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">user</span><span style="color:#710">'</span></span>], mysql[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">password</span><span style="color:#710">'</span></span>]) </pre></div> </div> </div> <p>The way you include the configuration might feel very convenient at a first glance, but imagine what happens when you get more configuration variables. You definitely need to provide an example configuration file. And it is hard to resist the temptation to include code within the configuration file.</p> <h2 id="json">JSON</h2> <p><a href="https://en.wikipedia.org/wiki/JSON">JSON</a> is short for JavaScript Object Notation. It is widespread and thus has good support for many programming languages.</p> <p>The configuration might look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>{ <span style="color:#606"><span style="color:#404">&quot;</span><span>mysql</span><span style="color:#404">&quot;</span></span>:{ <span style="color:#606"><span style="color:#404">&quot;</span><span>host</span><span style="color:#404">&quot;</span></span>:<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">localhost</span><span style="color:#710">&quot;</span></span>, <span style="color:#606"><span style="color:#404">&quot;</span><span>user</span><span style="color:#404">&quot;</span></span>:<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">root</span><span style="color:#710">&quot;</span></span>, <span style="color:#606"><span style="color:#404">&quot;</span><span>passwd</span><span style="color:#404">&quot;</span></span>:<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">my secret password</span><span style="color:#710">&quot;</span></span>, <span style="color:#606"><span style="color:#404">&quot;</span><span>db</span><span style="color:#404">&quot;</span></span>:<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">write-math</span><span style="color:#710">&quot;</span></span> }, <span style="color:#606"><span style="color:#404">&quot;</span><span>other</span><span style="color:#404">&quot;</span></span>:{ <span style="color:#606"><span style="color:#404">&quot;</span><span>preprocessing_queue</span><span style="color:#404">&quot;</span></span>:[ <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessing.scale_and_center</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessing.dot_reduction</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessing.connect_lines</span><span style="color:#710">&quot;</span></span> ], <span style="color:#606"><span style="color:#404">&quot;</span><span>use_anonymous</span><span style="color:#404">&quot;</span></span>:<span style="color:#088">true</span> } } </pre></div> </div> </div> <p>You can read it like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">json</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">config.json</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> json_data_file: data = json.load(json_data_file) print(data) </pre></div> </div> </div> <p>which outputs</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>{<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>: {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">db</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">write-math</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">host</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">localhost</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">passwd</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">my secret password</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">user</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">root</span><span style="color:#710">'</span></span>}, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>: {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">preprocessing_queue</span><span style="color:#710">'</span></span>: [<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">preprocessing.scale_and_center</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">preprocessing.dot_reduction</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">preprocessing.connect_lines</span><span style="color:#710">'</span></span>], <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">'</span><span style="color:#D20">use_anonymous</span><span style="color:#710">'</span></span>: <span style="color:#069">True</span>}} </pre></div> </div> </div> <p>Writing JSON files is also easy. Just build up the dictionary and use</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">json</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">config.json</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">w</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> outfile: json.dump(data, outfile) </pre></div> </div> </div> <h2 id="yaml">YAML</h2> <p><a href="https://en.wikipedia.org/wiki/YAML">YAML</a> is a configuration file format. Wikipedia says:</p> <blockquote> <p>YAML (rhymes with camel) is a human-readable data serialization format that takes concepts from programming languages such as C, Perl, and Python, and ideas from XML and the data format of electronic mail (RFC 2822). YAML was first proposed by Clark Evans in 2001, who designed it together with Ingy döt Net and Oren Ben-Kiki. It is available for several programming languages.</p> </blockquote> <p>The file itself might look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#606">mysql</span>: <span style="color:#606">host</span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">localhost</span></span> <span style="color:#606">user</span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">root</span></span> <span style="color:#606">passwd</span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">my secret password</span></span> <span style="color:#606">db</span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">write-math</span></span> <span style="color:#606">other</span>: <span style="color:#606">preprocessing_queue</span>: - <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">preprocessing.scale_and_center</span></span> - <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">preprocessing.dot_reduction</span></span> - <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">preprocessing.connect_lines</span></span> <span style="color:#606">use_anonymous</span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#D20">yes</span></span> </pre></div> </div> </div> <p>You can read it like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">yaml</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">config.yml</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">r</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">as</span> ymlfile: cfg = yaml.load(ymlfile) <span style="color:#080;font-weight:bold">for</span> section <span style="color:#080;font-weight:bold">in</span> cfg: print(section) print(cfg[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>]) print(cfg[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>]) </pre></div> </div> </div> <p>It outputs:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>other mysql {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">passwd</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">my secret password</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">host</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">localhost</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">db</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">write-math</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">user</span><span style="color:#710">'</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">root</span><span style="color:#710">'</span></span>} {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing_queue</span><span style="color:#710">'</span></span>: [<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing.scale_and_center</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing.dot_reduction</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing.connect_lines</span><span style="color:#710">'</span></span>], <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">use_anonymous</span><span style="color:#710">'</span></span>: <span style="color:#069">True</span>} </pre></div> </div> </div> <p>There is a <code>yaml.dump</code> method, so you can write the configuration the same way. Just build up a dictionary.</p> <p>YAML is used by the Blender project.</p> <h4 id="resources">Resources</h4> <ul> <li><a href="https://docs.python.org/3/library/configparser.html">Documentation</a></li> </ul> <h2 id="ini">INI</h2> <p>INI files look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[mysql] host=localhost user=root passwd=my secret password db=write-math [other] preprocessing_queue=[&quot;preprocessing.scale_and_center&quot;, &quot;preprocessing.dot_reduction&quot;, &quot;preprocessing.connect_lines&quot;] use_anonymous=yes </pre></div> </div> </div> <h3 id="configparser">ConfigParser</h3> <h4 id="basic-example">Basic example</h4> <p>The file can be loaded and used like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ConfigParser</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">io</span> <span style="color:#777"># Load the configuration file</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">config.yml</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">as</span> f: sample_config = f.read() config = ConfigParser.RawConfigParser(allow_no_value=<span style="color:#069">True</span>) config.readfp(io.BytesIO(sample_config)) <span style="color:#777"># List all contents</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">List all contents</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">for</span> section <span style="color:#080;font-weight:bold">in</span> config.sections(): print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Section: %s</span><span style="color:#710">&quot;</span></span> % section) <span style="color:#080;font-weight:bold">for</span> options <span style="color:#080;font-weight:bold">in</span> config.options(section): print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x %s:::%s:::%s</span><span style="color:#710">&quot;</span></span> % (options, config.get(section, options), <span style="color:#369;font-weight:bold">str</span>(<span style="color:#369;font-weight:bold">type</span>(options)))) <span style="color:#777"># Print some contents</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#b0b">\n</span><span style="color:#D20">Print some contents</span><span style="color:#710">&quot;</span></span>) print(config.get(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">use_anonymous</span><span style="color:#710">'</span></span>)) <span style="color:#777"># Just get the value</span> print(config.getboolean(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">use_anonymous</span><span style="color:#710">'</span></span>)) <span style="color:#777"># You know the datatype?</span> </pre></div> </div> </div> <p>which outputs</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>List <span style="color:#369;font-weight:bold">all</span> contents Section: mysql x host:::localhost:::&lt;<span style="color:#369;font-weight:bold">type</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">str</span><span style="color:#710">'</span></span>&gt; x user:::root:::&lt;<span style="color:#369;font-weight:bold">type</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">str</span><span style="color:#710">'</span></span>&gt; x passwd:::my secret password:::&lt;<span style="color:#369;font-weight:bold">type</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">str</span><span style="color:#710">'</span></span>&gt; x db:::write-math:::&lt;<span style="color:#369;font-weight:bold">type</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">str</span><span style="color:#710">'</span></span>&gt; Section: other x preprocessing_queue:::[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessing.scale_and_center</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessing.dot_reduction</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessing.connect_lines</span><span style="color:#710">&quot;</span></span>]:::&lt;<span style="color:#369;font-weight:bold">type</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">str</span><span style="color:#710">'</span></span>&gt; x use_anonymous:::yes:::&lt;<span style="color:#369;font-weight:bold">type</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">str</span><span style="color:#710">'</span></span>&gt; Print some contents yes <span style="color:#069">True</span> </pre></div> </div> </div> <p>As you can see, you can use a standard data format that is easy to read and write. Methods like <code>getboolean</code> and <code>getint</code> allow you to get the datatype instead of a simple string.</p> <h4 id="writing-configuration">Writing configuration</h4> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> configfile_name = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">config.yaml</span><span style="color:#710">&quot;</span></span> <span style="color:#777"># Check if there is already a configurtion file</span> <span style="color:#080;font-weight:bold">if</span> <span style="color:#080;font-weight:bold">not</span> os.path.isfile(configfile_name): <span style="color:#777"># Create the configuration file as it doesn't exist yet</span> cfgfile = <span style="color:#369;font-weight:bold">open</span>(configfile_name, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">w</span><span style="color:#710">'</span></span>) <span style="color:#777"># Add content to the file</span> Config = ConfigParser.ConfigParser() Config.add_section(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>) Config.set(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">host</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">localhost</span><span style="color:#710">'</span></span>) Config.set(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">user</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">root</span><span style="color:#710">'</span></span>) Config.set(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">passwd</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">my secret password</span><span style="color:#710">'</span></span>) Config.set(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mysql</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">db</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">write-math</span><span style="color:#710">'</span></span>) Config.add_section(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>) Config.set(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing_queue</span><span style="color:#710">'</span></span>, [<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing.scale_and_center</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing.dot_reduction</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">preprocessing.connect_lines</span><span style="color:#710">'</span></span>]) Config.set(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">other</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">use_anonymous</span><span style="color:#710">'</span></span>, <span style="color:#069">True</span>) Config.write(cfgfile) cfgfile.close() </pre></div> </div> </div> <p>results in</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[mysql] host = localhost user = root passwd = my secret password db = write-math [other] preprocessing_queue = ['preprocessing.scale_and_center', 'preprocessing.dot_reduction', 'preprocessing.connect_lines'] use_anonymous = True </pre></div> </div> </div> <h2 id="xml">XML</h2> <p>Seems not to be used at all for configuration files by the Python community. However, parsing / writing XML is easy and there are plenty of possibilities to do so with Python. One is BeautifulSoup:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">BeautifulSoup</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">BeautifulSoup</span> <span style="color:#080;font-weight:bold">with</span> <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">config.xml</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">as</span> f: content = f.read() y = BeautifulSoup(content) print(y.mysql.host.contents[<span style="color:#00D">0</span>]) <span style="color:#080;font-weight:bold">for</span> tag <span style="color:#080;font-weight:bold">in</span> y.other.preprocessing_queue: print(tag) </pre></div> </div> </div> <p>where the config.xml might look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;config&gt;</span> <span style="color:#070;font-weight:bold">&lt;mysql&gt;</span> <span style="color:#070;font-weight:bold">&lt;host&gt;</span>localhost<span style="color:#070;font-weight:bold">&lt;/host&gt;</span> <span style="color:#070;font-weight:bold">&lt;user&gt;</span>root<span style="color:#070;font-weight:bold">&lt;/user&gt;</span> <span style="color:#070;font-weight:bold">&lt;passwd&gt;</span>my secret password<span style="color:#070;font-weight:bold">&lt;/passwd&gt;</span> <span style="color:#070;font-weight:bold">&lt;db&gt;</span>write-math<span style="color:#070;font-weight:bold">&lt;/db&gt;</span> <span style="color:#070;font-weight:bold">&lt;/mysql&gt;</span> <span style="color:#070;font-weight:bold">&lt;other&gt;</span> <span style="color:#070;font-weight:bold">&lt;preprocessing_queue&gt;</span> <span style="color:#070;font-weight:bold">&lt;li&gt;</span>preprocessing.scale_and_center<span style="color:#070;font-weight:bold">&lt;/li&gt;</span> <span style="color:#070;font-weight:bold">&lt;li&gt;</span>preprocessing.dot_reduction<span style="color:#070;font-weight:bold">&lt;/li&gt;</span> <span style="color:#070;font-weight:bold">&lt;li&gt;</span>preprocessing.connect_lines<span style="color:#070;font-weight:bold">&lt;/li&gt;</span> <span style="color:#070;font-weight:bold">&lt;/preprocessing_queue&gt;</span> <span style="color:#070;font-weight:bold">&lt;use_anonymous</span> <span style="color:#b48">value</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;/other&gt;</span> <span style="color:#070;font-weight:bold">&lt;/config&gt;</span> </pre></div> </div> </div> <h2 id="file-endings">File Endings</h2> <p>File Endings give the user and the system an indicator about the content of a file. Reasonable file endings for configuration files are</p> <ul> <li><code>*config.py</code> for Python files</li> <li><code>*.yaml</code> or <code>*.yml</code> if the configuration is done in YAML format</li> <li><code>*.json</code> for configuration files written in JSON format</li> <li><code>*.cfg</code> or <code>*.conf</code> to indicate that it is a configuration file</li> <li><code>*.ini</code> for “initialization” are quite widespread (see <a href="https://en.wikipedia.org/wiki/INI_file">Wiki</a>)</li> <li><code>~/.[my_app_name]rc</code> is a VERY common naming scheme for configuration files on Linux systems. RC is a reference to an old computer system and means “run common”.</li> </ul> <p>That said, I think I prefer <code>*.conf</code>. I think it is a choice that users understand.</p> <p>But you might also consider that <code>*.ini</code> might get opened by standard in a text editor. For the other options, users might get asked which program they want to use.</p> <h2 id="resources-1">Resources</h2> <ul> <li><a href="http://json.parser.online.fr/">JSON Online Parser</a></li> <li><a href="http://stackoverflow.com/q/1726802/562769">What is the difference between YAML and JSON? When to prefer one over the other?</a></li> <li><a href="http://stackoverflow.com/q/791761/562769">Why do so many projects use XML for configuration files?</a></li> <li><a href="http://yamllint.com/">YAML Lint</a></li> <li><a href="http://i-tools.org/unserialize">INI file</a></li> </ul> Append Python PATH //martin-thoma.com/append-python-path/ Sun, 20 Jul 2014 14:04:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/append-python-path <p>Python has a <code>PATH</code> in which it looks for modules. You can display the current module PATH with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">sys</span> print(sys.path) </pre></div> </div> </div> <p>and apped something to it with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">sys</span> sys.path.append(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">/some/path/to/a/module</span><span style="color:#710">&quot;</span></span>) </pre></div> </div> </div> <p>However, the clean way would be to write a module and install that module.</p> Introduction to Octave //martin-thoma.com/introduction-to-octave/ Fri, 18 Jul 2014 17:40:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/introduction-to-octave <p><a href="https://en.wikipedia.org/wiki/GNU_Octave">GNU Octave</a> is a really neat prototyping language for machine learning tasks. It is dynamically typed.</p> <h2 id="installation">Installation</h2> <p>Octave is in the package repositories, so it can be installed by</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo apt-get install octave gnuplot-x11 octave-epstk </pre></div> </div> </div> <p>and started with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ octave </pre></div> </div> </div> <h2 id="configuration">Configuration</h2> <p>Create a file <code>~/.octaverc</code> in your home folder. Write</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>PS1('&gt;&gt;'); setenv(&quot;GNUTERM&quot;,&quot;x11&quot;); </pre></div> </div> </div> <p>in it to get a nicer prompt and make sure that plots will work.</p> <h2 id="the-language">The Language</h2> <h3 id="vectors-and-matrices">Vectors and Matrices</h3> <p>Octave has a lot of neat matrix manipulation features. You can create a matrix <code>$A = \begin{pmatrix} 1 &amp; 2\\ 3 &amp; 4\end{pmatrix}$</code> with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; A = [1 2; 3 4]; </pre></div> </div> </div> <p>When you want to transpose a vector / a matrix, you simply add an apostrophe:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; A = [1 2; 3 4]; &gt;&gt; A' ans = 1 3 2 4 </pre></div> </div> </div> <p>You can multiply two matrices with <code>A*B</code> or use the dot product with <code>A .* B</code>.</p> <p>The identity matrix <code>$I \in \mathbb{R}^{n \times n}$</code> can be created with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; I = eye(n); </pre></div> </div> </div> <p>You can get a part of the matrix by slicing:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; I = eye(n); &gt;&gt; I(:, 1:2); </pre></div> </div> </div> <p>But be careful: Vectors and matrices are 1-indexed, not 0-indexed as you might expect!</p> <p>You can get the size of a matrix with the function <code>size</code> which returns a matrix:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; a = [1 2 3; 4 5 6]; &gt;&gt; size(a) ans = 2 3 </pre></div> </div> </div> <p>If you simple want the “length” you can directly access the first element:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; size(a)(1) ans = 2 </pre></div> </div> </div> <h3 id="sequences">Sequences</h3> <p>The sequence <code>0 1 2 3 4 5</code> can be created with <code>[0:5]</code>.</p> <p>The sequence <code>0.2 0.3 0.4 0.5</code> can be created with <code>[0.2:0.1:0.5]</code>. In general: <code>[&lt;start&gt;:&lt;step&gt;:&lt;end&gt;]</code> where <code>&lt;start&gt;</code> and <code>&lt;end&gt;</code> are included.</p> <p>You can also very simple apply functions to each element:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; t = [0.2:0.1:0.5]; &gt;&gt; sin(t) ans = 0.19867 0.29552 0.38942 0.47943 </pre></div> </div> </div> <p>The output can be suppressed with <code>;</code>.</p> <h3 id="plotting">Plotting</h3> <p>I have never seen a language where plotting is so easy:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; x = [0:0.01:pi]; &gt;&gt; y = sin(x); &gt;&gt; plot(x, y); </pre></div> </div> </div> <p>You can add labels and a legend to it, too:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt; xlabel = &quot;x&quot;; &gt;&gt; ylabel = &quot;value&quot;; &gt;&gt; legend('sin', 'cos') &gt;&gt; title(&quot;sin and cos&quot;) </pre></div> </div> </div> <p>And finally, you can store the image:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>print -dpng 'my_plot.png' </pre></div> </div> </div> <h3 id="control-statements">Control statements</h3> <h4 id="for">for</h4> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>for i=1:10; printf(&quot;%i: %i\n&quot;, i, i^2) end </pre></div> </div> </div> <h4 id="while">while</h4> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>i=1; while i &lt;= 10, printf(&quot;%i: %i\n&quot;, i, i^2) end; </pre></div> </div> </div> <h4 id="if">if</h4> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>if 2 == 1+1, printf(&quot;True\n&quot;); elseif 3 == 2+1, printf(&quot;Else true&quot;); else printf(&quot;else&quot;); end; </pre></div> </div> </div> <h3 id="functions">Functions</h3> <p>Functions have to be saved in a file called <code>[filename].m</code>. One other special thing about functions is that you define the variable with the output at the beginning:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>function y = fibonacci(n) if n &lt; 2, y = 1; else y = fibonacci(n-1) + fibonacci(n-2); end; </pre></div> </div> </div> <p>You can also group values you want to give back like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>function [succ, pred] = succ_and_pred(n) succ = n+1; pred = n-1; </pre></div> </div> </div> <h2 id="resources">Resources</h2> <ul> <li><a href="https://en.wikipedia.org/wiki/GNU_Octave">GNU Octave</a></li> <li><a href="http://stackoverflow.com/questions/tagged/octave?sort=votes">stackoverflow.com</a></li> <li><a href="https://www.gnu.org/software/octave/doc/interpreter/">Documentation</a></li> </ul> Fix zypper readline error //martin-thoma.com/fix-zypper-libreadline-error/ Mon, 14 Jul 2014 11:34:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/fix-zypper-libreadline-error <p>In case you work on a openSUSE system and you get the following error</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ zypper zypper: symbol lookup error: /usr/lib/libreadline.so.6: undefined symbol: PC </pre></div> </div> </div> <p>you can probably “fix” it by setting the 64 Bit <code>LD_LIBRARY</code> like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ export LD_LIBRARY_PATH=/lib64:$LD_LIBRARY_PATH </pre></div> </div> </div> <p>It worked for me on openSUSE 12.1 “Asparagus”.</p> <h2 id="credits">Credits</h2> <p>Thanks to <a href="http://jrseti.blogspot.com/2011/09/zypper-does-not-work-on-opensuse-fixed.html">JRSETI’s Blog</a></p> Change password in ATIS //martin-thoma.com/change-password-in-atis/ Sat, 12 Jul 2014 17:24:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/change-password-in-atis <p>Recently, the <a href="https://en.wikipedia.org/wiki/Heartbleed">Heartbleed bug</a> was discovered. It works like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/xkcd/heartbleed_explanation.png"><img src="//martin-thoma.com/captions/heartbleed_explanation.png" alt="Heartbleed Explanation" width="375" height="800" class="" /></a><p class="wp-caption-text">Heartbleed Explanation<br />From <a href="http://xkcd.com/1354/">xkcd</a></p></div> <p>One effect of that bug is that you have to change your password.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/xkcd/heartbleed.png"><img src="//martin-thoma.com/captions/heartbleed.png" alt="Heartbleed" width="500" height="207" class="" /></a><p class="wp-caption-text">From <a href="http://xkcd.com/1353/">xkcd</a></p></div> <p>You can do that from home via SSH. Just replace <code>s_thoma</code> by <code>s_[your last name]</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ssh s_thoma@i08fs1.ira.uka.de s_thoma@i08fs1.ira.uka.de's password: s_thoma@i08fs1(~)$ passwd Changing password for user s_thoma. Enter login(AD) password: Current Password: New password: Retype new password: AD password information changed for s_thoma passwd: all authentication tokens updated successfully. s_thoma@i08fs1(~)$ exit logout Connection to i08fs1.ira.uka.de closed. </pre></div> </div> </div> <p>In case you don’t remember your password: Take a look at your Browser settings. You’ve probably entered it already for looking at your printing account and eventually your browser saved it.</p> A.I. in Computer Games //martin-thoma.com/ai-in-computer-games/ Tue, 01 Jul 2014 23:52:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ai-in-computer-games <p>Artificial Intelligences (A.I.s) are computer programs that are able to adjust their behaviour according to data they see. So A.I.s are able to adjust to the data a human player generates.</p> <figure> <img src="http://imgs.xkcd.com/comics/game_ais.png" alt="Game A.I.s" /> <figcaption>Game A.I.s</figcaption> </figure> <h2 id="solved-games">Solved games</h2> <p>There is a number of games which are definitely solved. That means the A.I. plays perfectly:</p> <ul> <li>Tic-Tac-Toe</li> <li>Connect Four: <a href="http://www.informatik.uni-trier.de/~fernau/DSL0607/Masterthesis-Viergewinnt.pdf">A Knowledge-based Approach of Connect-Four</a>. Amsterdam, 1988. Victor Allis.</li> <li>Checkers:</li> </ul> <p>See also: <a href="https://en.wikipedia.org/wiki/Solved_game">Solved Game</a></p> <h2 id="computers-win-always">Computers win always</h2> <p>A second category are games in which A.I.s always win against human players, but they don’t have a perfect strategy. Or at least we have not proven that they have a perfect strategy:</p> <ul> <li>Chess</li> <li>Go on a 5×5 board</li> <li>Reversi on a 4×4 board</li> </ul> <p>Update: There are advances on the 19×19 field:</p> <ul> <li><a href="https://storage.googleapis.com/deepmind-data/assets/papers/deepmind-mastering-go.pdf">Paper</a></li> <li>Nature: <a href="http://www.nature.com/nature/journal/v529/n7587/full/nature16961.html">Mastering the game of Go with deep neural networks and tree search</a></li> <li>YouTube by nature: <a href="https://www.youtube.com/watch?v=g-dKXOlsf98">The computer that mastered Go</a></li> <li>Google Blog: <a href="https://googleblog.blogspot.de/2016/01/alphago-machine-learning-game-go.html">AlphaGo: using machine learning to master the ancient game of Go</a></li> </ul> <h2 id="unspecialized-game-ais">Unspecialized Game A.I.s</h2> <p>The following video is an explanation and demo of software Tom Murphy VII wrote that learns how to play a Nintendo Entertainment System game and then automatically plays it. It’s called “learnfun” (for learn function).</p> <p>You might want to skip to 6:13 for the demo:</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/xOCurBYI_gY" frameborder="0" allowfullscreen=""></iframe> <p>Research paper published in SIGBOVIK 2013: “<a href="http://tom7.org/mario/mario.pdf">The first level of Super Mario Bros. is easy with lexicographic ordering a and time travel …after that it gets a little tricky</a>.”</p> <p>There is a follow-up video with Zelda, Punch-Out, Dr. Mario, Contra, Wall Street Kid and Russian Attack:</p> <iframe width="512" height="288" src="//www.youtube.com/embed/YGJHR9Ovszs?list=UU3azLjQuz9s5qk76KEXaTvA" frameborder="0" allowfullscreen=""></iframe> <p>And a third episode with Super Mario, Gradius, Mega Man 2, Pro Wrestling, Color a Dinosaur, Nintendo Pinball, Cliffhanger, Arkanoid, Double Dare, Ice hockey:</p> <iframe width="512" height="288" src="//www.youtube.com/embed/Q-WgQcnessA" frameborder="0" allowfullscreen=""></iframe> <h2 id="super-mario-ai-competition">Super Mario A.I. Competition</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/bBZ7kEphv3s?start=385" frameborder="0" allowfullscreen=""></iframe> Linux Commands for Working from home //martin-thoma.com/linux-commands-for-working-from-home/ Mon, 30 Jun 2014 13:41:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/linux-commands-for-working-from-home <p>This article is just a collection of commands and shortcuts I need quite often.</p> <h2 id="creating-a-single-archive-file-from-a-complete-folder">Creating a single archive file from a complete folder</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ tar -zcvf ~/[target file].tar.gz [folder you want to copy] </pre></div> </div> </div> <h2 id="getting-a-file-from-a-remote-host-to-localhost">Getting a file from a remote host to localhost</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ scp [username]@[host]:[path/to/remote/file] [path/to/local/folder] </pre></div> </div> </div> <h2 id="shell-shortcuts">Shell Shortcuts</h2> <p>Copy a selected text:</p> <p><kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>C</kbd></p> <p>Paste a text from clipboard to the command line:</p> <p><kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>V</kbd></p> <p>Copy a selected text from the command line and paste it:</p> <p><kbd>Mouse wheel click</kbd></p> <p>Search through the history of commands you have typed before:</p> <p><kbd>Ctrl</kbd> + <kbd>R</kbd></p> <h2 id="web-stuff">Web stuff</h2> <p>### Watching the Apache error log</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ tail -f /var/log/apache2/error.log </pre></div> </div> </div> <h3 id="truncating-the-apache-error-log">Truncating the Apache error log</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo truncate -s 0 /var/log/apache2/error.log </pre></div> </div> </div> <h3 id="finding-phpini">Finding php.ini</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ php -i | grep &quot;Loaded Configuration File&quot; </pre></div> </div> </div> <h3 id="importing-data-to-mysql">Importing data to MySQL</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mysql --host localhost -u root -p write-math &lt; wm_raw_draw_data.sql </pre></div> </div> </div> What are pfiles? //martin-thoma.com/what-are-pfiles/ Fri, 27 Jun 2014 06:39:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-are-pfiles <p>pfile is a binary file format that is used in <abbr title="Automatic Speech Recognition">ASR</abbr> for storing feature vectors and their corresponding labels. This file format is sometimes also called <abbr title="International Computer ScienceInstitute">ICSI</abbr> feature file archive format. But this file format cannot be used for ASR only, but also for many other <abbr title="Machine Learning">ML</abbr> tasks.</p> <blockquote> <p>The file consists of a fixed length ascii header followed by zero or more variable length binary sections. Each parameter in the header has a name and a list of zero or more value strings. The programmer’s interface to pfiles (see param.h and pfile.h) allows each parameter value to be interpreted as integer, float, string, arrays, distributed vector, matrix, mapping tables, etc.</p> <p>Some special parameter names are associated with a section in the binary part of the pfile. The value strings for these parameters give the size and offset (from the end of the header) of the binary section.</p> <p>A binary section can be used as a one dimensional sequence of values, or as a sequence of fixed length rows in a two dimensional matrix.</p> <p>Some parameters are automatically added by the pfile command. For example, pfile_header is a parameter that contains the length and version number of the header.</p> </blockquote> <p>Source: <a href="http://old-site.clsp.jhu.edu/ws96/ris/man/pfile.doc">old-site.clsp.jhu.edu/ws96/ris/man/pfile.doc</a></p> <h2 id="pfileutils">pfile_utils</h2> <p><code>pfile_utils</code> is a toolset to manage pfiles. It is part of the <a href="http://www1.icsi.berkeley.edu/~dpwe/projects/sprach/sprachcore.html">SPRACHcore software package</a>. The project is located at <a href="https://code.google.com/p/pfile-utilities">code.google.com/p/pfile-utilities</a> and seems to be in version 0.51 by now. The code is written in C++.</p> <p><code>pfile_info</code> gives general information about the file:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ pfile_info all.pfile all.pfile 9581 sentences, 3158027 frames, 1 label(s), 42 features </pre></div> </div> </div> <h3 id="pfilecreate">pfile_create</h3> <p>You can call pfile_create like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ./pfile_create -i - -f 1 -l 1 -o output.pfile 0 0 1 1 0 1 2 0 0 2 1 1 0 3 1 1 0 4 42 4 1 0 0 0 1 1 1337 0 1 2 2 2 2 0 3 3 </pre></div> </div> </div> <p>You can end the input with <kbd>Ctrl</kbd> + <kbd>D</kbd>.</p> <p>The numbers are:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[sentence-nr] [frame-nr] [feature 1] [feature 2] ... [feature n] [label 1] [label 2] ... [label n] </pre></div> </div> </div> <p>where the option <code>-f</code> defines the number of features and <code>-l</code> defines the number of labels. Please note that within one sentence, the number of frames has to be increasing by exactly one. One sentence can have an arbitrary number of frames, but as soon as you make another sentence, you need to increase this number by exactly one.</p> <h2 id="see-also">See also</h2> <ul> <li><a href="http://www1.icsi.berkeley.edu/Speech/faq/ftrformats.html">ICSI Speech FAQ: 3.3 What are the feature data formats?</a></li> </ul> Awesome Robots //martin-thoma.com/awesome-robots/ Sun, 22 Jun 2014 22:39:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/awesome-robots <p>Robots are mechanical devices that are controlled by computer programs. Some of them act unexpectedly intelligent due to recent improvements in processing speed (hardware) and <a href="https://en.wikipedia.org/wiki/Neural_net">neural nets</a> (computer science) as well as good application of <a href="https://en.wikipedia.org/wiki/Differential_equation">differential equations</a> (mathematics).</p> <p>Differential equations are mathematical equations with a function and its derivative. So a simple differential equation is <code>$f(x) = f'(x)$</code>. They are commonly used in physics, because you often have functions that have time as their argument. A simple example would be the growth of a population in biology (see <a href="http://www.animations.physics.unsw.edu.au/jw/DifferentialEquations.htm">Differential Equations: some simple examples from Physclips</a>).</p> <h2 id="cubli">Cubli</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/n_6p-1J551Y" frameborder="0" allowfullscreen=""></iframe> <p>The Cubli is a 15 × 15 × 15 cm cube that can jump up and balance on its corner. Reaction wheels mounted on three faces of the cube rotate at high angular velocities and then brake suddenly, causing the Cubli to jump up. Once the Cubli has almost reached the corner stand up position, controlled motor torques are applied to make it balance on its corner. In addition to balancing, the motor torques can also be used to achieve a controlled fall such that the Cubli can be commanded to fall in any arbitrary direction. Combining these three abilities – jumping up, balancing, and controlled falling – the Cubli is able to ‘walk’.</p> <h2 id="quadcopters-by-raffaello-dandrea">Quadcopters by Raffaello D’Andrea</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/w2itwFJCgFQ" frameborder="0" allowfullscreen=""></iframe> <p>In a robot lab at TEDGlobal, Raffaello D’Andrea demos his flying quadcopters: robots that think like athletes, solving physical problems with algorithms that help them learn. In a series of nifty demos, D’Andrea show drones that play catch, balance and make decisions together – and watch out for an I-want-this-now demo of Kinect-controlled quads.</p> <h2 id="kuka-table-tennis-robot">Kuka Table Tennis Robot</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/tIIJME8-au8" frameborder="0" allowfullscreen=""></iframe> <p>The unbelievably fast KUKA robot faces off against one of the best table tennis players of all time. Who has the best technique? Who will win the first ever table tennis duel of human versus robot?</p> <p>Watch this thrilling commercial of table tennis and robotics performed at the highest level. The KUKA KR AGILUS demonstrates its skills with the table tennis racket - a realistic vision of what robots can be capable of in the future.</p> <p>Timo Boll, the German table tennis star, is the new brand ambassador for KUKA Robotics in China. The collaboration celebrates the inherent speed, precision, and flexibility of KUKA’s industrial robots in tandem with Boll’s electrifying and tactical prowess in competition. To celebrate the new KUKA Robotics factory in Shanghai, the thrilling video was a highlight of the Grand Opening on March 11th, 2014. The 20,000 sq. meter space will produce the KR QUANTEC series robot as well as the KRC4 universal controller for the Asian market. As a market leader in China, KUKA aims to further develop automation in the country while providing a modern and employee-friendly working environment.</p> <p>More: <a href="http://www.kuka-timoboll.com">kuka-timoboll.com</a></p> <h2 id="stickybot">Stickybot</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/o5lMJtQOKSY" frameborder="0" allowfullscreen=""></iframe> <p>A gecko-like robot from Stanford.</p> <h2 id="cheetah">Cheetah</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/chPanW0QWhA" frameborder="0" allowfullscreen=""></iframe> <p>A robot by <a href="https://en.wikipedia.org/wiki/Boston_Dynamics">Boston Dynamics</a> that runs 45 km/h!</p> <h2 id="snakebot">Snakebot</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/8VLjDjXzTiU" frameborder="0" allowfullscreen=""></iframe> <p>From the Biorobotics Lab at Carnegie Mellon University, a snake robot (Snakebot) demonstrates how it can climb a tree and look around.</p> <p>Please keep in mind that this robot climbed a specific tree with a specific trunk width about 1 meter off of the ground. The researchers working to design, build and program these robots still have much work to do to get these bots to climb taller trees of various sizes and to navigate over branches and wires.</p> <h2 id="kilobots">Kilobots</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/G1t4M2XnIhI" frameborder="0" allowfullscreen=""></iframe> <p>A thousand-robot swarm created by Harvard researchers can self-assemble into different shapes. Learn more: <a href="http://spectrum.ieee.org/automaton/robotics/robotics-hardware/a-thousand-kilobots-self-assemble">A Thousand Kilobots Self-Assemble Into Complex Shapes</a></p> Classify MNIST with PyBrain //martin-thoma.com/classify-mnist-with-pybrain/ Wed, 18 Jun 2014 02:31:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/classify-mnist-with-pybrain <p>The <abbr title="Mixed National Institute of Standards and Technology">MNIST</abbr> database is a huge database of handwritten digits that is commonly used for training, evaluating and comparing classifiers.</p> <p>It has a training set of 60,000 instances and a test set of 10,000 instances. Every instance is a 28 × 28 pixel grayscale image.</p> <h2 id="the-mnist-format">The MNIST format</h2> <p>MNIST comes in 4 files (<a href="http://yann.lecun.com/exdb/mnist/">download here</a>):</p> <ul> <li>train-images-idx3-ubyte.gz: training set images (9.45 MB, 60000 instances)</li> <li>train-labels-idx1-ubyte.gz: training set labels (28.2 kB, 60000 labels)</li> <li>t10k-images-idx3-ubyte.gz: test set images (1.57 MB, 10000 instances)</li> <li>t10k-labels-idx1-ubyte.gz: test set labels (4.43 kB, 10000 labels)</li> </ul> <p>Both label files are like this:</p> <pre><code>[offset] [type] [value] [description] 0000 32 bit integer 0x00000801(2049) magic number (MSB first) 0004 32 bit integer 60000 number of items 0008 unsigned byte ?? label 0009 unsigned byte ?? label ........ xxxx unsigned byte ?? label The labels values are 0 to 9. </code></pre> <p>and both image containers are like that:</p> <pre><code>[offset] [type] [value] [description] 0000 32 bit integer 0x00000803(2051) magic number 0004 32 bit integer 60000 number of images 0008 32 bit integer 28 number of rows 0012 32 bit integer 28 number of columns 0016 unsigned byte ?? pixel 0017 unsigned byte ?? pixel ........ xxxx unsigned byte ?? pixel </code></pre> <p>And they are, of course, compressed.</p> <h2 id="reading-the-dataset">Reading the dataset</h2> <p>Python brings all necessary tools to make it easy to read the dataset:</p> <ul> <li><a href="https://docs.python.org/2/library/gzip.html">gzip</a>: A library for reading gzipped files</li> <li><a href="https://docs.python.org/2/library/struct.html#struct.unpack">unpack</a> to read the packed binary data</li> </ul> <p>As the training and the testing dataset is structured the same way, we can create a method thad retrives the data for both files.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">struct</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">unpack</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">gzip</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">zeros</span>, <span style="color:#B44;font-weight:bold">uint8</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">get_labeled_data</span>(imagefile, labelfile): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Read input-vector (image) and target class (label, 0-9) and return</span><span> </span><span> it as list of tuples.</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#777"># Open the images with gzip in read binary mode</span> images = gzip.open(imagefile, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rb</span><span style="color:#710">'</span></span>) labels = gzip.open(labelfile, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rb</span><span style="color:#710">'</span></span>) <span style="color:#777"># Read the binary data</span> <span style="color:#777"># We have to get big endian unsigned int. So we need '&gt;I'</span> <span style="color:#777"># Get metadata for images</span> images.read(<span style="color:#00D">4</span>) <span style="color:#777"># skip the magic_number</span> number_of_images = images.read(<span style="color:#00D">4</span>) number_of_images = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, number_of_images)[<span style="color:#00D">0</span>] rows = images.read(<span style="color:#00D">4</span>) rows = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, rows)[<span style="color:#00D">0</span>] cols = images.read(<span style="color:#00D">4</span>) cols = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, cols)[<span style="color:#00D">0</span>] <span style="color:#777"># Get metadata for labels</span> labels.read(<span style="color:#00D">4</span>) <span style="color:#777"># skip the magic_number</span> N = labels.read(<span style="color:#00D">4</span>) N = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, N)[<span style="color:#00D">0</span>] <span style="color:#080;font-weight:bold">if</span> number_of_images != N: <span style="color:#080;font-weight:bold">raise</span> <span style="color:#C00;font-weight:bold">Exception</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">number of labels did not match the number of images</span><span style="color:#710">'</span></span>) <span style="color:#777"># Get the data</span> x = zeros((N, rows, cols), dtype=uint8) <span style="color:#777"># Initialize numpy array</span> y = zeros((N, <span style="color:#00D">1</span>), dtype=uint8) <span style="color:#777"># Initialize numpy array</span> <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(N): <span style="color:#080;font-weight:bold">if</span> i % <span style="color:#00D">1000</span> == <span style="color:#00D">0</span>: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">i: %i</span><span style="color:#710">&quot;</span></span> % i) <span style="color:#080;font-weight:bold">for</span> row <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(rows): <span style="color:#080;font-weight:bold">for</span> col <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(cols): tmp_pixel = images.read(<span style="color:#00D">1</span>) <span style="color:#777"># Just a single byte</span> tmp_pixel = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;B</span><span style="color:#710">'</span></span>, tmp_pixel)[<span style="color:#00D">0</span>] x[i][row][col] = tmp_pixel tmp_label = labels.read(<span style="color:#00D">1</span>) y[i] = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;B</span><span style="color:#710">'</span></span>, tmp_label)[<span style="color:#00D">0</span>] <span style="color:#080;font-weight:bold">return</span> (x, y) </pre></div> </div> </div> <h2 id="viewing-data">Viewing data</h2> <p>You might want to take a look at an image. This is easily possible with <a href="http://wiki.scipy.org/PyLab">PyLab</a> (which is a part of Matplotlib):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pylab</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">imshow</span>, <span style="color:#B44;font-weight:bold">show</span>, <span style="color:#B44;font-weight:bold">cm</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">view_image</span>(image, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span>): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>View a single image.</span><span style="color:black">&quot;&quot;&quot;</span></span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Label: %s</span><span style="color:#710">&quot;</span></span> % label) imshow(image, cmap=cm.gray) show() </pre></div> </div> </div> <p>It tooks like this:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/06/mnist-1.png" class="image"><img src="//martin-thoma.com/captions/mnist-1.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">7</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/06/mnist-2.png" class="image"><img src="//martin-thoma.com/captions/mnist-2.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">2</div></div></li></ul> <h2 id="classify-data">Classify data</h2> <p>Now we can use <a href="http://pybrain.org/">PyBrain</a> to classify data.</p> <p>The following code will first build the PyBrain datastructure for the training set and the testing set. Then it will build a very simple neural network called a <em>Multilayer Perceptron</em> (MLP) with three layers: An input layer, a hidden layer and an output layer.</p> <p>After creating it, the MLP will be trained with the backpropagation algorithm. Every training step is followed by an evaluation step.</p> <p>By the way, <a href="http://docs.scipy.org/doc/numpy/reference/generated/numpy.ravel.html"><code>numpy.ravel</code></a> simply flattens a list.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ravel</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.datasets</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ClassificationDataSet</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.utilities</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">percentError</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.tools.shortcuts</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">buildNetwork</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.supervised.trainers</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">BackpropTrainer</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.structure.modules</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">SoftmaxLayer</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">classify</span>(training, testing, HIDDEN_NEURONS, MOMENTUM, WEIGHTDECAY, LEARNING_RATE, LEARNING_RATE_DECAY, EPOCHS): trndata = ClassificationDataSet(INPUT_FEATURES, <span style="color:#00D">1</span>, nb_classes=CLASSES) tstdata = ClassificationDataSet(INPUT_FEATURES, <span style="color:#00D">1</span>, nb_classes=CLASSES) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(testing)): tstdata.addSample(ravel(testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>][i]), [testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>][i]]) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(trndata)): trndata.addSample(ravel(trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>][i]), [trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>][i]]) <span style="color:#777"># This is necessary, but I don't know why</span> <span style="color:#777"># See http://stackoverflow.com/q/8154674/562769</span> trndata._convertToOneOfMany() tstdata._convertToOneOfMany() fnn = buildNetwork(trndata.indim, HIDDEN_NEURONS, trndata.outdim, outclass=SoftmaxLayer) trainer = BackpropTrainer(fnn, dataset=trndata, momentum=MOMENTUM, verbose=<span style="color:#069">True</span>, weightdecay=WEIGHTDECAY, learningrate=LEARNING_RATE, lrdecay=LEARNING_RATE_DECAY) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(EPOCHS): trainer.trainEpochs(<span style="color:#00D">1</span>) trnresult = percentError(trainer.testOnClassData(), trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>]) tstresult = percentError(trainer.testOnClassData( dataset=tstdata), tstdata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>]) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">epoch: %4d</span><span style="color:#710">&quot;</span></span> % trainer.totalepochs, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> train error: %5.2f%%</span><span style="color:#710">&quot;</span></span> % trnresult, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> test error: %5.2f%%</span><span style="color:#710">&quot;</span></span> % tstresult) <span style="color:#080;font-weight:bold">return</span> fnn </pre></div> </div> </div> <h2 id="final-steps">Final steps</h2> <p>You might want to add <a href="//martin-thoma.com/how-to-parse-command-line-arguments-in-python/">command line parameters</a>, <a href="https://docs.python.org/2/library/logging.html">logging</a> and probably <a href="https://docs.python.org/2/library/pickle.html#module-cPickle">pickle</a> the data.</p> <h2 id="final-complete-code">Final complete code</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">struct</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">unpack</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">gzip</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">numpy</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">zeros</span>, <span style="color:#B44;font-weight:bold">uint8</span>, <span style="color:#B44;font-weight:bold">ravel</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pylab</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">imshow</span>, <span style="color:#B44;font-weight:bold">show</span>, <span style="color:#B44;font-weight:bold">cm</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.datasets</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ClassificationDataSet</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.utilities</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">percentError</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.tools.shortcuts</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">buildNetwork</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.supervised.trainers</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">BackpropTrainer</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.structure.modules</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">SoftmaxLayer</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os.path</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">cPickle</span> <span style="color:#080;font-weight:bold">as</span> pickle <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">get_labeled_data</span>(imagefile, labelfile, picklename): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Read input-vector (image) and target class (label, 0-9) and return</span><span> </span><span> it as list of tuples.</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">if</span> os.path.isfile(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">%s.pickle</span><span style="color:#710">'</span></span> % picklename): data = pickle.load(<span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">%s.pickle</span><span style="color:#710">'</span></span> % picklename)) <span style="color:#080;font-weight:bold">else</span>: <span style="color:#777"># Open the images with gzip in read binary mode</span> images = gzip.open(imagefile, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rb</span><span style="color:#710">'</span></span>) labels = gzip.open(labelfile, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rb</span><span style="color:#710">'</span></span>) <span style="color:#777"># Read the binary data</span> <span style="color:#777"># We have to get big endian unsigned int. So we need '&gt;I'</span> <span style="color:#777"># Get metadata for images</span> images.read(<span style="color:#00D">4</span>) <span style="color:#777"># skip the magic_number</span> number_of_images = images.read(<span style="color:#00D">4</span>) number_of_images = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, number_of_images)[<span style="color:#00D">0</span>] rows = images.read(<span style="color:#00D">4</span>) rows = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, rows)[<span style="color:#00D">0</span>] cols = images.read(<span style="color:#00D">4</span>) cols = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, cols)[<span style="color:#00D">0</span>] <span style="color:#777"># Get metadata for labels</span> labels.read(<span style="color:#00D">4</span>) <span style="color:#777"># skip the magic_number</span> N = labels.read(<span style="color:#00D">4</span>) N = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;I</span><span style="color:#710">'</span></span>, N)[<span style="color:#00D">0</span>] <span style="color:#080;font-weight:bold">if</span> number_of_images != N: <span style="color:#080;font-weight:bold">raise</span> <span style="color:#C00;font-weight:bold">Exception</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">The number of labels did not match </span><span style="color:#710">'</span></span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">the number of images.</span><span style="color:#710">'</span></span>) <span style="color:#777"># Get the data</span> x = zeros((N, rows, cols), dtype=uint8) <span style="color:#777"># Initialize numpy array</span> y = zeros((N, <span style="color:#00D">1</span>), dtype=uint8) <span style="color:#777"># Initialize numpy array</span> <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(N): <span style="color:#080;font-weight:bold">if</span> i % <span style="color:#00D">1000</span> == <span style="color:#00D">0</span>: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">i: %i</span><span style="color:#710">&quot;</span></span> % i) <span style="color:#080;font-weight:bold">for</span> row <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(rows): <span style="color:#080;font-weight:bold">for</span> col <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(cols): tmp_pixel = images.read(<span style="color:#00D">1</span>) <span style="color:#777"># Just a single byte</span> tmp_pixel = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;B</span><span style="color:#710">'</span></span>, tmp_pixel)[<span style="color:#00D">0</span>] x[i][row][col] = (<span style="color:#369;font-weight:bold">float</span>(tmp_pixel) / <span style="color:#00D">255</span>) tmp_label = labels.read(<span style="color:#00D">1</span>) y[i] = unpack(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&gt;B</span><span style="color:#710">'</span></span>, tmp_label)[<span style="color:#00D">0</span>] data = {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>: x, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>: y, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rows</span><span style="color:#710">'</span></span>: rows, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">cols</span><span style="color:#710">'</span></span>: cols} pickle.dump(data, <span style="color:#369;font-weight:bold">open</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">%s.pickle</span><span style="color:#710">&quot;</span></span> % picklename, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">wb</span><span style="color:#710">&quot;</span></span>)) <span style="color:#080;font-weight:bold">return</span> data <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">view_image</span>(image, label=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span>): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>View a single image.</span><span style="color:black">&quot;&quot;&quot;</span></span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Label: %s</span><span style="color:#710">&quot;</span></span> % label) imshow(image, cmap=cm.gray) show() <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">classify</span>(training, testing, HIDDEN_NEURONS, MOMENTUM, WEIGHTDECAY, LEARNING_RATE, LEARNING_RATE_DECAY, EPOCHS): INPUT_FEATURES = testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">rows</span><span style="color:#710">'</span></span>] * testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">cols</span><span style="color:#710">'</span></span>] print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Input features: %i</span><span style="color:#710">&quot;</span></span> % INPUT_FEATURES) CLASSES = <span style="color:#00D">10</span> trndata = ClassificationDataSet(INPUT_FEATURES, <span style="color:#00D">1</span>, nb_classes=CLASSES) tstdata = ClassificationDataSet(INPUT_FEATURES, <span style="color:#00D">1</span>, nb_classes=CLASSES) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>])): tstdata.addSample(ravel(testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>][i]), [testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>][i]]) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(training[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>])): trndata.addSample(ravel(training[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>][i]), [training[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">y</span><span style="color:#710">'</span></span>][i]]) <span style="color:#777"># This is necessary, but I don't know why</span> <span style="color:#777"># See http://stackoverflow.com/q/8154674/562769</span> trndata._convertToOneOfMany() tstdata._convertToOneOfMany() fnn = buildNetwork(trndata.indim, HIDDEN_NEURONS, trndata.outdim, outclass=SoftmaxLayer) trainer = BackpropTrainer(fnn, dataset=trndata, momentum=MOMENTUM, verbose=<span style="color:#069">True</span>, weightdecay=WEIGHTDECAY, learningrate=LEARNING_RATE, lrdecay=LEARNING_RATE_DECAY) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(EPOCHS): trainer.trainEpochs(<span style="color:#00D">1</span>) trnresult = percentError(trainer.testOnClassData(), trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>]) tstresult = percentError(trainer.testOnClassData( dataset=tstdata), tstdata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>]) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">epoch: %4d</span><span style="color:#710">&quot;</span></span> % trainer.totalepochs, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> train error: %5.2f%%</span><span style="color:#710">&quot;</span></span> % trnresult, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> test error: %5.2f%%</span><span style="color:#710">&quot;</span></span> % tstresult) <span style="color:#080;font-weight:bold">return</span> fnn <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: parser = ArgumentParser() <span style="color:#777"># Add more options if you like</span> parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-H</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">H</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">int</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hidden_neurons</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">200</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">number of neurons in the hidden layer</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-e</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">EPOCHS</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">int</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">epochs</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">20</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">number of epochs to learn</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-d</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">W</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">float</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">weightdecay</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#60E">0.01</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">weightdecay</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-m</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">M</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">float</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">momentum</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#60E">0.1</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">momentum</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-l</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">ETA</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">float</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">learning_rate</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#60E">0.01</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">learning rate</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-ld</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">ALPHA</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">float</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">lrdecay</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">1</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">learning rate decay</span><span style="color:#710">&quot;</span></span>) args = parser.parse_args() print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Get testset</span><span style="color:#710">&quot;</span></span>) testing = get_labeled_data(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">t10k-images-idx3-ubyte.gz</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">t10k-labels-idx1-ubyte.gz</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">testing</span><span style="color:#710">'</span></span>) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Got %i testing datasets.</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">len</span>(testing[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>])) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Get trainingset</span><span style="color:#710">&quot;</span></span>) training = get_labeled_data(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train-images-idx3-ubyte.gz</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">train-labels-idx1-ubyte.gz</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">training</span><span style="color:#710">'</span></span>) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Got %i training datasets.</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">len</span>(training[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>])) classify(training, testing, args.hidden_neurons, args.momentum, args.weightdecay, args.learning_rate, args.lrdecay, args.epochs) </pre></div> </div> </div> <h2 id="results">Results</h2> <p>I’ll update that tomorrow:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>python pybrainmnist.py -e 10000 -H 300 Get testset Got 10000 testing datasets. Get trainingset Got 60000 training datasets. Input features: 784 Total error: 0.0473157733222 ('epoch: 1', ' train error: 89.56%', ' test error: 89.72%') Total error: 0.0471086288906 ('epoch: 2', ' train error: 90.13%', ' test error: 90.20%') Total error: 0.0471545599893 ('epoch: 3', ' train error: 90.25%', ' test error: 90.26%') Total error: 0.0471544804653 ('epoch: 4', ' train error: 90.08%', ' test error: 89.91%') Total error: 0.047137394504 ('epoch: 5', ' train error: 90.25%', ' test error: 90.26%') Total error: 0.0471630159397 ('epoch: 6', ' train error: 89.56%', ' test error: 89.72%') Total error: 0.0471585130872 ('epoch: 7', ' train error: 89.78%', ' test error: 89.90%') Total error: 0.0471376594558 ('epoch: 8', ' train error: 90.14%', ' test error: 90.42%') Total error: 0.0471355052763 ('epoch: 9', ' train error: 90.97%', ' test error: 91.08%') Total error: 0.0471595886207 ('epoch: 10', ' train error: 90.07%', ' test error: 89.68%') Total error: 0.0471580212242 ('epoch: 11', ' train error: 90.13%', ' test error: 90.20%') Total error: 0.047146194285 ('epoch: 12', ' train error: 90.07%', ' test error: 89.68%') Total error: 0.047139885027 ('epoch: 13', ' train error: 89.56%', ' test error: 89.72%') Total error: 0.0471459617826 ('epoch: 14', ' train error: 90.13%', ' test error: 90.20%') Total error: 0.0471302472029 ('epoch: 15', ' train error: 90.07%', ' test error: 89.68%') Total error: 0.0471525497087 ('epoch: 16', ' train error: 90.26%', ' test error: 90.18%') Total error: 0.0471419186775 ('epoch: 17', ' train error: 90.97%', ' test error: 91.08%') Total error: 0.0471563384617 ('epoch: 18', ' train error: 88.76%', ' test error: 88.65%') Total error: 0.0471480887109 ('epoch: 19', ' train error: 90.97%', ' test error: 91.08%') Total error: 0.0471466129654 ('epoch: 20', ' train error: 90.08%', ' test error: 89.91%') Total error: 0.0471322920471 ('epoch: 21', ' train error: 90.08%', ' test error: 89.91%') Total error: 0.0471505302295 ('epoch: 22', ' train error: 88.76%', ' test error: 88.65%') Total error: 0.0471490334095 ('epoch: 23', ' train error: 90.97%', ' test error: 91.08%') Total error: 0.0471643256975 ('epoch: 24', ' train error: 90.25%', ' test error: 90.26%') Total error: 0.0471597744749 ('epoch: 25', ' train error: 88.76%', ' test error: 88.65%') </pre></div> </div> </div> <p>This took several hours :-/</p> Classification with PyBrain //martin-thoma.com/classification-with-pybrain/ Mon, 16 Jun 2014 01:02:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/classification-with-pybrain <p>PyBrain is a Python library for machine learning. It’s in version 0.31 and the last change is 2 months ago (<a href="https://github.com/pybrain/pybrain">source</a>). The source code is licensed under <a href="https://tldrlegal.com/license/bsd-3-clause-license-(revised)">BSD 3 Clause License</a>. The <a href="http://pybrain.org/docs/">documentation</a> is usable, but for from perfect.</p> <h2 id="classification-example">Classification example</h2> <p>The following is a slightly modified example from the documentation. It shows how PyBrain starts learning to classify 2-dimensional datapoints into 3 classes:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#777"># Source: http://pybrain.org/docs/tutorial/fnn.html</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.datasets</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ClassificationDataSet</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.utilities</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">percentError</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.tools.shortcuts</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">buildNetwork</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.supervised.trainers</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">BackpropTrainer</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pybrain.structure.modules</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">SoftmaxLayer</span> <span style="color:#777"># Only needed for data generation and graphical output</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">pylab</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ion</span>, <span style="color:#B44;font-weight:bold">ioff</span>, <span style="color:#B44;font-weight:bold">figure</span>, <span style="color:#B44;font-weight:bold">draw</span>, <span style="color:#B44;font-weight:bold">contourf</span>, <span style="color:#B44;font-weight:bold">clf</span>, <span style="color:#B44;font-weight:bold">show</span>, <span style="color:#B44;font-weight:bold">plot</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">scipy</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">diag</span>, <span style="color:#B44;font-weight:bold">arange</span>, <span style="color:#B44;font-weight:bold">meshgrid</span>, <span style="color:#B44;font-weight:bold">where</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">numpy.random</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">multivariate_normal</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">random</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">normalvariate</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">generate_data</span>(n=<span style="color:#00D">400</span>): INPUT_FEATURES = <span style="color:#00D">2</span> CLASSES = <span style="color:#00D">3</span> means = [(-<span style="color:#00D">1</span>, <span style="color:#00D">0</span>), (<span style="color:#00D">2</span>, <span style="color:#00D">4</span>), (<span style="color:#00D">3</span>, <span style="color:#00D">1</span>)] cov = [diag([<span style="color:#00D">1</span>, <span style="color:#00D">1</span>]), diag([<span style="color:#60E">0.5</span>, <span style="color:#60E">1.2</span>]), diag([<span style="color:#60E">1.5</span>, <span style="color:#60E">0.7</span>])] alldata = ClassificationDataSet(INPUT_FEATURES, <span style="color:#00D">1</span>, nb_classes=CLASSES) minX, maxX = means[<span style="color:#00D">0</span>][<span style="color:#00D">0</span>], means[<span style="color:#00D">0</span>][<span style="color:#00D">0</span>] minY, maxY = means[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>], means[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>] <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(n): <span style="color:#080;font-weight:bold">for</span> klass <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(CLASSES): features = multivariate_normal(means[klass], cov[klass]) x, y = features minX, maxX = <span style="color:#369;font-weight:bold">min</span>(minX, x), <span style="color:#369;font-weight:bold">max</span>(maxX, x) minY, maxY = <span style="color:#369;font-weight:bold">min</span>(minY, y), <span style="color:#369;font-weight:bold">max</span>(maxY, y) alldata.addSample(features, [klass]) <span style="color:#080;font-weight:bold">return</span> {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">minX</span><span style="color:#710">'</span></span>: minX, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">maxX</span><span style="color:#710">'</span></span>: maxX, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">minY</span><span style="color:#710">'</span></span>: minY, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">maxY</span><span style="color:#710">'</span></span>: maxY, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">d</span><span style="color:#710">'</span></span>: alldata} <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">generate_data2</span>(n=<span style="color:#00D">400</span>): alldata = ClassificationDataSet(<span style="color:#00D">2</span>, <span style="color:#00D">1</span>, nb_classes=<span style="color:#00D">2</span>) minX, maxX = <span style="color:#00D">3</span>, <span style="color:#00D">3</span> minY, maxY = <span style="color:#00D">2</span>, <span style="color:#00D">2</span> <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">1000</span>): x = normalvariate(<span style="color:#00D">3</span>, <span style="color:#60E">0.6</span>) y = normalvariate(<span style="color:#00D">2</span>, <span style="color:#00D">1</span>) minX, maxX = <span style="color:#369;font-weight:bold">min</span>(minX, x), <span style="color:#369;font-weight:bold">max</span>(maxX, x) minY, maxY = <span style="color:#369;font-weight:bold">min</span>(minY, y), <span style="color:#369;font-weight:bold">max</span>(maxY, y) alldata.addSample((x, y), (<span style="color:#00D">0</span>,)) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">1000</span>): x = normalvariate(<span style="color:#00D">7</span>, <span style="color:#60E">0.5</span>) y = normalvariate(<span style="color:#00D">1</span>, <span style="color:#60E">0.1</span>) alldata.addSample((x, y), (<span style="color:#00D">1</span>,)) <span style="color:#080;font-weight:bold">return</span> {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">minX</span><span style="color:#710">'</span></span>: minX, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">maxX</span><span style="color:#710">'</span></span>: maxX, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">minY</span><span style="color:#710">'</span></span>: minY, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">maxY</span><span style="color:#710">'</span></span>: maxY, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">d</span><span style="color:#710">'</span></span>: alldata} <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">perceptron</span>(hidden_neurons=<span style="color:#00D">5</span>, weightdecay=<span style="color:#60E">0.01</span>, momentum=<span style="color:#60E">0.1</span>): INPUT_FEATURES = <span style="color:#00D">2</span> CLASSES = <span style="color:#00D">3</span> HIDDEN_NEURONS = hidden_neurons WEIGHTDECAY = weightdecay MOMENTUM = momentum <span style="color:#777"># Generate the labeled set</span> g = generate_data() <span style="color:#777">#g = generate_data2()</span> alldata = g[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">d</span><span style="color:#710">'</span></span>] minX, maxX, minY, maxY = g[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">minX</span><span style="color:#710">'</span></span>], g[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">maxX</span><span style="color:#710">'</span></span>], g[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">minY</span><span style="color:#710">'</span></span>], g[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">maxY</span><span style="color:#710">'</span></span>] <span style="color:#777"># Split data into test and training dataset</span> tstdata, trndata = alldata.splitWithProportion(<span style="color:#60E">0.25</span>) trndata._convertToOneOfMany() <span style="color:#777"># This is necessary, but I don't know why</span> tstdata._convertToOneOfMany() <span style="color:#777"># http://stackoverflow.com/q/8154674/562769</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Number of training patterns: %i</span><span style="color:#710">&quot;</span></span> % <span style="color:#369;font-weight:bold">len</span>(trndata)) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Input and output dimensions: %i, %i</span><span style="color:#710">&quot;</span></span> % (trndata.indim, trndata.outdim)) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Hidden neurons: %i</span><span style="color:#710">&quot;</span></span> % HIDDEN_NEURONS) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">First sample (input, target, class):</span><span style="color:#710">&quot;</span></span>) print(trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">input</span><span style="color:#710">'</span></span>][<span style="color:#00D">0</span>], trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">target</span><span style="color:#710">'</span></span>][<span style="color:#00D">0</span>], trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>][<span style="color:#00D">0</span>]) fnn = buildNetwork(trndata.indim, HIDDEN_NEURONS, trndata.outdim, outclass=SoftmaxLayer) trainer = BackpropTrainer(fnn, dataset=trndata, momentum=MOMENTUM, verbose=<span style="color:#069">True</span>, weightdecay=WEIGHTDECAY) <span style="color:#777"># Visualization</span> ticksX = arange(minX-<span style="color:#00D">1</span>, maxX+<span style="color:#00D">1</span>, <span style="color:#60E">0.2</span>) ticksY = arange(minY-<span style="color:#00D">1</span>, maxY+<span style="color:#00D">1</span>, <span style="color:#60E">0.2</span>) X, Y = meshgrid(ticksX, ticksY) <span style="color:#777"># need column vectors in dataset, not arrays</span> griddata = ClassificationDataSet(INPUT_FEATURES, <span style="color:#00D">1</span>, nb_classes=CLASSES) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(X.size): griddata.addSample([X.ravel()[i], Y.ravel()[i]], [<span style="color:#00D">0</span>]) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">20</span>): trainer.trainEpochs(<span style="color:#00D">1</span>) trnresult = percentError(trainer.testOnClassData(), trndata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>]) tstresult = percentError(trainer.testOnClassData( dataset=tstdata), tstdata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>]) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">epoch: %4d</span><span style="color:#710">&quot;</span></span> % trainer.totalepochs, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> train error: %5.2f%%</span><span style="color:#710">&quot;</span></span> % trnresult, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> test error: %5.2f%%</span><span style="color:#710">&quot;</span></span> % tstresult) out = fnn.activateOnDataset(griddata) <span style="color:#777"># the highest output activation gives the class</span> out = out.argmax(axis=<span style="color:#00D">1</span>) out = out.reshape(X.shape) figure(<span style="color:#00D">1</span>) <span style="color:#777"># always print on the same canvas</span> ioff() <span style="color:#777"># interactive graphics off</span> clf() <span style="color:#777"># clear the plot</span> <span style="color:#080;font-weight:bold">for</span> c <span style="color:#080;font-weight:bold">in</span> [<span style="color:#00D">0</span>, <span style="color:#00D">1</span>, <span style="color:#00D">2</span>]: here, _ = where(tstdata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">class</span><span style="color:#710">'</span></span>] == c) plot(tstdata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">input</span><span style="color:#710">'</span></span>][here, <span style="color:#00D">0</span>], tstdata[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">input</span><span style="color:#710">'</span></span>][here, <span style="color:#00D">1</span>], <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">o</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">if</span> out.max() != out.min(): <span style="color:#777"># safety check against flat field</span> contourf(X, Y, out) <span style="color:#777"># plot the contour</span> ion() <span style="color:#777"># interactive graphics on</span> draw() <span style="color:#777"># update the plot</span> ioff() show() <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">__main__</span><span style="color:#710">'</span></span>: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span>, <span style="color:#B44;font-weight:bold">ArgumentDefaultsHelpFormatter</span> parser = ArgumentParser(formatter_class=ArgumentDefaultsHelpFormatter) <span style="color:#777"># Add more options if you like</span> parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-H</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">H</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">int</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hidden_neurons</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">5</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">number of neurons in the hidden layer</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-d</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">W</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">float</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">weightdecay</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#60E">0.01</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">weightdecay</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-m</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">M</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#369;font-weight:bold">float</span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">momentum</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#60E">0.1</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">momentum</span><span style="color:#710">&quot;</span></span>) args = parser.parse_args() perceptron(args.hidden_neurons, args.weightdecay, args.momentum) </pre></div> </div> </div> <p>See it in action:</p> <iframe width="420" height="315" src="//www.youtube.com/embed/FjvO3zqVYSw" frameborder="0" allowfullscreen=""></iframe> <h2 id="resources">Resources</h2> <ul> <li><a href="http://pybrain.org/">Official website</a></li> <li>StackExchange <ul> <li><a href="http://stackoverflow.com/questions/tagged/pybrain">StackOverflow</a>: 134 questions</li> <li><a href="http://stats.stackexchange.com/search?q=pybrain">stats.SE</a></li> </ul> </li> <li><a href="http://www.reddit.com/r/MachineLearning/search?q=pybrain&amp;restrict_sr=on">reddit.com/r/MachineLearning</a></li> </ul> Reference Management with JabRef //martin-thoma.com/reference-management-with-jabref/ Sun, 15 Jun 2014 20:51:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/reference-management-with-jabref <p>Keeping track of papers, articles and books or more general sources you can cite is a task you will have to tackle when you’re writing your thesis. One way to store information is via BibTeX files.</p> <p>BibTeX is a reference management software that is used together with LaTeX. If you’re new to BibTeX or references in LaTeX in general you could read the followin articles:</p> <ul> <li><a href="http://tex.stackexchange.com/q/25701/5645">bibtex vs. biber and biblatex vs. natbib</a></li> <li><a href="http://tex.stackexchange.com/q/8411/5645">What is the difference between bibtex and biblatex?</a> - I keep forgetting that all the time.</li> </ul> <p>I’ve tried to create a <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/biblatex-mwe">MWE for biblatex</a>, but as I don’t really know much about BibTeX it’s probably not the best resource to start with.</p> <p>A longer <a href="https://github.com/MartinThoma/write-math/tree/master/bachelor-arbeit">working example of BibTeX</a> is my bachelors thesis (work is still in (slow) progress).</p> <h2 id="what-is-jabref">What is JabRef?</h2> <p><a href="https://en.wikipedia.org/wiki/JabRef">JabRef</a> is a reference management software that uses BibTeX as its native format. It looks like this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/06/jabref.png"><img src="//martin-thoma.com/captions/jabref.png" alt="JabRef" width="500" height="272" class="" /></a><p class="wp-caption-text">JabRef</p></div> <h2 id="how-can-i-get-it">How can I get it?</h2> <p>JabRef 2.10 beta is part of the Debian sources. Thus it can be installed by</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install jabref </pre></div> </div> </div> <p>The official development page is <a href="http://jabref.sourceforge.net/">jabref.sourceforge.net</a>. As it is written in Java it can be installed on all (or at least most) systems where you have a JVM (thus: good news Windows / Mac users!).</p> <h2 id="whats-good-about-jabref">What’s good about JabRef?</h2> <p>You can easily add the information where the PDF is located on your system and open the PDF directly via JabRef:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/06/jabref-pdf.png"><img src="//martin-thoma.com/captions/jabref-pdf.png" alt="Adding PDF with JabRef" width="500" height="209" class="" /></a><p class="wp-caption-text">Adding PDF with JabRef</p></div> <p>This is especially powerfull with the search. As you can add quite a lot of information to the entries (such as the abstract and comments) and searching that is faster / easier than searching folders of PDFs, it’s very convenient to use JabRef for opening your PDFs:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/06/jabref-searching.png"><img src="//martin-thoma.com/captions/jabref-searching.png" alt="Searching with JabRef" width="500" height="238" class="" /></a><p class="wp-caption-text">Searching with JabRef</p></div> <p>The preview also helps you to see how it might appear in your document:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/06/jabref-preview.png"><img src="//martin-thoma.com/captions/jabref-preview.png" alt="JabRef preview" width="500" height="182" class="" /></a><p class="wp-caption-text">JabRef preview</p></div> <p>Another nice feature is the autocompletion of authors names and titles.</p> <h2 id="what-could-be-better">What could be better?</h2> <p>It would be neat if you could automatically upload your BibTeX file and use other peoples BibTeX files to <strong>complete the information</strong> or to get informed of possible errors in your database.</p> <p>Additionally, a good <strong>PDF reader</strong> that is fast and allows annotations of which JabRef would be aware would be awesome.</p> <p><strong>Speed</strong> is quite often an issue with Java applications in my experience. It takes about 5 seconds to open my BibTeX file of about 37 references. After starting that it’s ok.</p> <p><strong>Shortcuts</strong> are important for tools that get used often, too. Although JabRef has some reasonable shortcuts like <kbd>Ctr</kbd>+<kbd>i</kbd> for importing a BibTeX file and <kbd>Ctr</kbd>+<kbd>s</kbd> for saving the current BibTeX file, I miss <kbd>Ctrl</kbd>+<kbd>f</kbd> for searching the database.</p> <p><strong>Importing</strong> other BibTeX files into the current BibTeX file is possible. But I would also like to “import” BibTeX data by copy and pasting a single dataset.</p> <h2 id="alternatives">Alternatives</h2> <p><a href="https://en.wikipedia.org/wiki/Mendeley">Mendeley</a> is a closed-source alternative with a built-in PDF reader. It seems to be fast and can complete information when the title is given.</p> Discussions with friends //martin-thoma.com/discussions-with-friends/ Sat, 10 May 2014 02:04:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/discussions-with-friends <p>I’ve recently had a very interesting discussion with some friends. We talked about a lot of stuff and I don’t want to go into detail about the topics we’ve discussed, but rather some thoughts about discussions.</p> <h2 id="types-of-discussions">Types of discussions</h2> <p>There are many ways people talk to each other:</p> <ul> <li><strong>Small Talk</strong> is about being together and feeling fine. We do it when we are together waiting for something or just because it feels good. It’s not so much about content which show discussions about weather, fashion or sitcoms, although the amount of information you exchange varies quite a lot.</li> <li><strong>Feelings</strong> and talking about feelings is difficult, but important. Although I tend to say it’s like small talk, but I don’t want to go into detail here.</li> <li><strong>Teaching</strong> is a situation where one person knows more than another person in some topic he (or she) teaches the other.</li> <li><strong>Learning</strong> is either the other side in the teaching situation or learning together. I think it is fundamentally different and deserves an own bullet point because in the teaching situation, the teacher leads the conversation. In the learning situation you don’t have somebody who leads the conversation. It’s a free flow of (hopefully) constructive thoughts with the aim to get a new ability as a group.</li> <li><strong>Moral or Political Discussions</strong> are some sort of learning, but in contrast to learning in the sense that you get another ability or get to know some more facts, the aim is on evaluating how to weight those facts. Discussions involve a learning part, but the core is about putting things together. So it is not mainly about what could be done but what should be done and for what reasons.</li> </ul> <h2 id="whats-special-about-discussions">What’s special about discussions?</h2> <p>Discussions involve some aim. That aim might be</p> <ul> <li>What is the best way to explain XYZ? What does best mean in this context?</li> <li>What should we do in situation ABC? What is to consider for what reasons?</li> </ul> <p>But very much of the conversations that are labeled as “discussions” feel rather like small talk for the following reasons:</p> <p>I think to have a meaningful discussion you need to have a partner who is not of your opinion. For political discussions this means the following are NOT meaningful statements:</p> <ul> <li>I want everybody to be able to find a job (or shorter: Fight unemployment)</li> <li>I want to make less dept</li> <li>I want everybody to be able to live a healthy live</li> <li>I want to help families</li> <li>I want everybody to be happy</li> </ul> <p>All these three statements are statements that everybody could agree with. But you get reasonable statements when you tell how to do so.</p> <p>You can also talk about the “order”: I want to make less dept, but when young families have to pay more than 20 Euro per year more it is not acceptable. Of course, that’s still much to vague, but I think you get the point. Telling what you value might help people to intuitively decide with which person they could rather identify, but it is not enough to name reasons.</p> <p>Another important part of a meaningful discussion is that it should in theory be possible to change the mind of the other person. This is the reason why I’ve called it “discussions with friends”. In contrast to the truth-finding “discussions” you have in science, you don’t need to be able to say what observations could <strong><a href="https://en.wikipedia.org/wiki/Falsifiability">falsify</a></strong> your theory. But if you go into a discussion and you know that it is impossible that the other - no matter how good he makes his point - convinces you of his opinion, you’re actually not having a discussion. You try to teach them. (And it’s a bad type of teaching.)</p> <h2 id="techniques-to-take-most-out-of-discussions">Techniques to take most out of discussions</h2> <p>It is difficult to be open minded in a good discussion. You might need to end a discussion and think through it some time after you had it. Because we tend to defend a point of view when we begin to defend it, no matter how good the other makes his point. It is very difficult to honestly say: Yes, you’re correct. That changes the case and probably my opinion.<br /> And you should not say so too fast. Some people are charismatic, some can speak or write very good. When you hear a new argument the first time, you might have difficulties to find a correct counter argument. But when you’re with friends you should be able to say:</p> <blockquote> <p>That’s the first time I’ve heard that. I have to think about it.</p> </blockquote> <p>or something like</p> <blockquote> <p>I’ve never seen it from that perspective.</p> </blockquote> <p>People like to teach and this makes them feel more comfortable discussing with you. You don’t give up your opinion with statements like these, but it’s simply being honest.</p> <p>Speaking of honesty, there is a similar DON’T: Don’t say something like</p> <blockquote> <p>Yes, I agree with you, but [Whatever he just said negated]</p> </blockquote> <p>I hear this so often in political debates by amateurs who have read something about discussions. By agreeing you make it easier for your discussion partner to agree with you (he can’t disagree when you agree with him, can he?), but it should be a honest way to agree. It’s a very bad step to fake agreement.</p> <h2 id="group-dynamics">Group dynamics</h2> <p>Always - and that’s not only related to discussions - try to think what and how the other thinks. Sometimes when a group discusses, a single person get’s isolated and has to defend his point of view alone. That’s ok. But don’t make it worse for him:</p> <ul> <li>Give him enough time to think and to talk.</li> <li>Only one person and argument at a time. It’s difficult to switch and to concentrate on two (or even more) separate discussions.</li> <li>Try to support him when he has trouble with finding the correct words or the best way to express himself. It is difficult to tell when you simply have to wait and give him some time to think and when you should try to support him.</li> </ul> <h2 id="know-when-youre-wrong">Know when you’re wrong</h2> <p>Changing opinions is difficult. Especially if you have them for a long time or when you’ve already defended them. It’s a little bit like an investment. When you’ve already spend 6,000 Euro for an investment and there is a tiny chance that you will get what you want but a growing chance that the investment was just a bad idea and probability suggest to change the investment and rescue what’s left, most people will not do so. Somehow we quite often tend to a all-or-nothing thinking which is suboptimal in many cases.</p> <p>So, what can we do so to figure that out for ourselves? Sometimes it is impossible to do so while discussing, but after the discussion you can think about it:</p> <ul> <li>What arguments did I tell the others? How did I tell them? What were counter arguments? Are they valid? If so / not: Why?</li> <li>Are there arguments I’ve missed?</li> <li>Do I feel comfortable with my arguments? Why do I think they could be weak? What do I think are strong arguments? Do others also think that those arguments are strong?</li> </ul> <p>If you’re not sure about it, you can continue it. It should not be a simple repetition of arguments, but a new discussion with a new structure of arguments. If you’re still not sure after many arguments, you can make a pro / contra list.</p> <p>Please note:</p> <ul> <li>It’s not important what the majority thinks. However, it might be an indicator.</li> <li>Some arguments might simply be wrong. But don’t make this choice too easily.</li> <li>Some arguments might be irrelevant. I tend to think “How does this impact my life?”. If an argument has no impact or simply assumes an unrealistic situation, it might be irrelevant.</li> <li>You don’t have to agree at the end. A honest disagreement where both sides understand the arguments of the other side is much better than a comprise that no side really thinks is good.</li> </ul> <p>And I want to note that discussions might have many equally valid answers, whereas science has only one correct answer (which might be difficult to find / almost impossible to decide which thesis is correct, but there is only one).</p> HTML5 Template //martin-thoma.com/html5-template/ Sat, 03 May 2014 20:43:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/html5-template <p>Once in a while I need to create simple HTML pages. This is the template I use:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#34b">&lt;!doctype html&gt;</span> <span style="color:#070;font-weight:bold">&lt;html</span> <span style="color:#b48">lang</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">en</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;head&gt;</span> <span style="color:#070;font-weight:bold">&lt;meta</span> <span style="color:#b48">charset</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">utf-8</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;title&gt;</span>TODO<span style="color:#070;font-weight:bold">&lt;/title&gt;</span> <span style="color:#070;font-weight:bold">&lt;/head&gt;</span> <span style="color:#070;font-weight:bold">&lt;body&gt;</span> <span style="color:#070;font-weight:bold">&lt;h1&gt;</span>TODO<span style="color:#070;font-weight:bold">&lt;/h1&gt;</span> <span style="color:#070;font-weight:bold">&lt;/body&gt;</span> <span style="color:#070;font-weight:bold">&lt;/html&gt;</span> </pre></div> </div> </div> <p>and as a sublime snippet:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;snippet&gt;</span> <span style="color:#070;font-weight:bold">&lt;content&gt;</span><span style="font-weight:bold;color:#666">&lt;![CDATA[</span> &lt;!doctype html&gt; &lt;html lang=&quot;en&quot;&gt; &lt;head&gt; &lt;meta charset=&quot;utf-8&quot; /&gt; &lt;title&gt;${1:Title}&lt;/title&gt; &lt;/head&gt; &lt;body&gt; &lt;h1&gt;${2:Header}&lt;/h1&gt; ${3:Content} &lt;/body&gt; &lt;/html&gt; <span style="font-weight:bold;color:#666">]]&gt;</span><span style="color:#070;font-weight:bold">&lt;/content&gt;</span> <span style="color:#070;font-weight:bold">&lt;tabTrigger&gt;</span>html5<span style="color:#070;font-weight:bold">&lt;/tabTrigger&gt;</span> <span style="color:#777">&lt;!-- Optional: Set a scope to limit where the snippet will trigger --&gt;</span> <span style="color:#777">&lt;!-- &lt;scope&gt;source.python&lt;/scope&gt; --&gt;</span> <span style="color:#070;font-weight:bold">&lt;/snippet&gt;</span> </pre></div> </div> </div> Prüfungsverwaltung am KIT //martin-thoma.com/pruefungsanmeldungen-am-kit/ Tue, 08 Apr 2014 16:09:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/pruefungsanmeldungen-am-kit <!-- <div class="info">This article is about an idea how to give students the possibility to proof that they were registered for an exam.</div> --> <p>Gerade ist mir aufgefallen, dass ich nicht zur Prüfung “Programmierparadigmen” angemeldet bin. Dabei war ich mir relativ sicher, mich sogar am ersten Tag angemeldet zu haben, als die Anmeldung freigeschaltet wurde.</p> <p>Meiner Meinung nach sind wir Studenten hier in einer ungerechtfertigt schlechten Position: Sollte tatsächlich ein Fehler passiert sein und meine Anmeldung nicht funktioniert haben bzw. die Anmeldung (wie oder warum auch immer) rückgängig gemacht worden sein, habe ich keinerlei Möglichkeit zu beweisen, dass ich angemeldet war und nicht etwa es einfach vergessen habe. Was ich in meinem konkreten Fall nicht ausschließen will, schließlich ist das schon zwei Monate her und ich habe mich für einige Prüfungen angemeldet und keine automatische Bestätigung der Anmeldung erhalten.</p> <h2 id="verbesserungsvorschlag">Verbesserungsvorschlag</h2> <p>Kurz und gut: Ich will, dass die Uni ein digitales Signaturverfahren einsetzt und die technischen Möglichkeiten nutzt, um den Studenten zu helfen ihre Rechte durchzusetzen. Wie das genau funktionieren soll, wird im Folgenden erklärt.</p> <h3 id="ausfhrlich">Ausführlich</h3> <p>Zur Verbesserung dieser Situation schlage ich folgendes vor:</p> <p>Studenten sollen die Möglichkeit bekommen, einen öffentlichen Schlüssel hochzuladen:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/04/kit-pgp-personal-data.png"><img src="//martin-thoma.com/captions/kit-pgp-personal-data.png" alt="Einen Schlüssel hinzufügen" width="500" height="237" class="" /></a><p class="wp-caption-text">Einen Schlüssel hinzufügen</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/04/kit-pgp-personal-management.png"><img src="//martin-thoma.com/captions/kit-pgp-personal-management.png" alt="Einen Schlüssel hinzufügen" width="500" height="317" class="" /></a><p class="wp-caption-text">Einen Schlüssel hinzufügen</p></div> <p>Mit diesem signieren sie Prüfungsanmeldungen:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/04/kit-pgp-pruefungsanmeldung-signieren.png"><img src="//martin-thoma.com/captions/kit-pgp-pruefungsanmeldung-signieren.png" alt="Prüfungsanmeldung signieren" width="500" height="250" class="" /></a><p class="wp-caption-text">Prüfungsanmeldung signieren</p></div> <p>Bei jeder Prüfungsanmeldung soll innerhalb von 24h eine E-Mail in Textform (keine PDF) an u<em>**</em>@student.kit.edu, also die KIT E-Mail-Adresse des Studenten, geschickt werden, der sich angemeldet hat.</p> <p>Diese E-Mail soll folgendes beinhalten:</p> <ul> <li>Alle Prüfungen (mit Name, Termin der Prüfung, letzter An- und Abmeldetermin), zu den der Student angemeldet ist.</li> <li>Der volle Name und die Matrikelnummer des Studenten.</li> <li>Das Datum der E-Mail.</li> </ul> <p>Diese E-Mail soll mit einem offiziellen KIT Schlüssel signiert werden. Dies könnte z.B. mit PGP gemacht werden und würde dann etwa so aussehen:</p> <blockquote> <p>—–BEGIN PGP SIGNED MESSAGE—–<br /> Hash: SHA1<br /> <br /> Student: Martin Thoma (Matrikelnummer: 1612345)<br /> Zeitpunkt: 08.04.2014, 12:34:56 Uhr<br /> Angemeldete Prüfungen:<br /> * Programmierparadigmen (Prüfungstermin: 10.04.2014; letzter Termin der Anmeldung: 31.03.2014; letzer Termin der Abmeldung: 08.04.2014)<br /> * Kognitive Systeme (Prüfungstermin: 11.04.2014; letzter Termin der Anmeldung: 15.03.2014; letzer Termin der Abmeldung: 10.04.2014)<br /> <br /> —–BEGIN PGP SIGNATURE—–<br /> Version: GnuPG v1.4.14 (GNU/Linux)<br /> <br /> iEYEARECAAYFAlNDzBoACgkQO3Q6GUuCW82z+ACfamkVC/S8HIpASH8F0ZGVbVW1<br /> rgwAn2cRvNeDN3pZVTpvNWV1vYK9f1fI<br /> =3DvZU7<br /> —–END PGP SIGNATURE—–</p> </blockquote> <p>Der Student sollte jederzeit die Möglichkeit haben, eine wie oben beschriebene signierte E-Mail mit der Liste der Prüfungen und einem Datum zu erhalten.</p> <p>Nun sollen Studenten in der Klausur die Möglichkeit haben, diese E-Mail auf einem USB-Stick mitzubringen. Die Aufsicht müsste also einen Computer haben, mit dem sie die E-Mail anschauen und insbesondere die Signatur überprüfen können. So könnte ein Student, der einmal zu einer Klausur angemeldet das auch belegen.</p> <h3 id="abmeldungen">Abmeldungen</h3> <p>Die auf den ersten Blick sehr schöne Lösung hat einen wichtigen Schönheitsfehler: Studenten können sich von Prüfungen abmelden. Daher ist es möglich, dass ein Student eine signierte E-Mail hat, die ihm die Anmeldung zur Prüfung bestätigt, er aber dennoch nicht zur Prüfung angemeldet ist, da er sich abgemeldet hat.</p> <p>Deshalb wäre es nötig, dass jeder Student ein eigenes Schlüsselpaar aus einem öffentlichen und einem privaten Schlüssel erstellt. Wenn sich ein Student von der Prüfung abmeldet, bekommt er einen Text, z. B. etwas in dieser Richtung:</p> <blockquote> <p>Ich, Martin Thoma (Matrikelnummer: 1612345), melde mich hiermit am 08.04.2014 um 12:34:56 Uhr von der Prüfung “Programmierparadigmen” (Prüfungsdatum: 10.04.2014) ab.</p> </blockquote> <p>Diese muss er mit seinem privaten Schlüssel signieren. Die Uni muss daher den öffentlichen Schlüssel des Studenten kennen und diesem zugeordnet haben. Sobald die Abmeldung eingegangen ist, wird innerhalb von 24h eine Bestätigung an den Studenten verschickt, die von der oben beschriebenen Form ist.</p> <p>oder auch eine Fehlermitteilung:</p> <blockquote> <p>Sehr geehrter Herr Thoma,<br /> die Signatur ihrer Nachricht war ungültig. Bitte überprüfen Sie, ob Sie den korrekten privaten Schlüssel verwendet haben.</p> </blockquote> <p>Nun hätte auch die Klausuraufsicht die Möglichkeit zu belegen, dass ein Student sich von der Prüfung abgemeldet hat.</p> <h3 id="technik-afinitt">Technik-Afinität</h3> <p>Was ist mit Studenten, die es nicht schaffen ein Schlüsselpaar zu erzeugen bzw. eine Nachricht zu signieren?</p> <p>Nun, das ist einfach: Wer keinen öffentlichen Schlüssel hinterlegt, bekommt auch keine signierten Nachrichten. Dennoch sollten diese Studenten die E-Mails, wie sie oben beschrieben wurden, bekommen. Dann weiß man als Student, dass vermutlich alles mit der Anmeldung geklappt hat bzw. wenn die E-Mail nicht kommt, dass etwas nicht geklappt hat.</p> <p>Bevor also die erste signierte E-Mail der Uni an den Studenten geschrieben wird, muss der Student seinen öffentlichen Schlüssel der Uni mitgeteilt haben und eine Nachricht mit dem privaten Schlüssel signiert haben. Damit wird sichergestellt, dass der Student prinzipiell in der Lage ist sich von Prüfungen abzumelden.</p> <h3 id="student-verliert-schlssel">Student verliert Schlüssel</h3> <p>Was macht man, wenn ein Student einmal einen Schlüssel eingericht hat, diesen aber verliert?</p> <p>Was passiert, wenn man seinen Studentenausweis verliert? Ich denke die Vorgehensweise wäre dann ähnlich.</p> <p>Vorstellbar wäre etwas in der Art:</p> <ul> <li>Der Student muss zum Studienbüro und Schriftlich bestätigen, dass der öffentliche Schlüssel aus dem KIT-System entfernt wird und damit ungültig wird.</li> <li>Der Student muss sich bei allen Professoren persönlich melden und unterschreiben, wenn er sich von der Klausur abmelden will.</li> </ul> <h2 id="pgp---was-ist-das">PGP - Was ist das?</h2> <p>Siehe <a href="https://de.wikipedia.org/wiki/Pretty_Good_Privacy">Wikpedia</a>.</p> <p>Es ist für folgende Systeme verfügbar:</p> <ul> <li>Linux, siehe z.B. <a href="http://wiki.ubuntuusers.de/GnuPG">Ubuntu mit GnuPG</a></li> <li>Windows, siehe z.B. <a href="http://www.gpg4win.org/index-de.html">GPG4Win</a></li> <li>Mac, siehe z.B. <a href="http://sourceforge.net/projects/macgpg/">Mac GNU Privacy Guard</a></li> </ul> <p>Eine weitere Erklärung ist im <a href="https://wiki.piratenpartei.de/PGP">Piratenwiki</a>.</p> <h2 id="einfgen-ins-system">Einfügen ins System</h2> <p>Die Website <a href="http://www.wechall.net/">wechall.net</a> bietet die Möglichkeit, einen PGP-Schlüssel hochzuladen. Sobald man das gemacht hat, werden dort alle Nachrichten mit dem öffentlichen Schlüssel verschlüsselt. Der Quellcode der Seite ist <a href="https://www.wechall.net/de/wechall.zip">hier</a> verfügbar.</p> <p>Mit PHP scheint das ganze sehr einfach zu sein (<a href="http://stackoverflow.com/q/15969740/562769">Quelle</a>). Auch mit Python sieht die Sache sehr leicht aus (<a href="https://pythonhosted.org/python-gnupg/">Quelle</a>).</p> <p>Da ich keine Ahnung habe was für campus.kit.edu verwendet wird, kann ich hier leider nicht mehr dazu sagen.</p> <p>Dann würde man noch eine Tabelle in der Datenbank benötigen. Die würde etwa so aussehen:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">CREATE</span> <span style="color:#339;font-weight:bold">TABLE</span> <span style="color:#080;font-weight:bold">IF</span> <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#080;font-weight:bold">EXISTS</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">openpgp_keys</span><span style="color:#710">&quot;</span></span> ( <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">id</span><span style="color:#710">&quot;</span></span> <span style="color:#0a8;font-weight:bold">int</span>(<span style="color:#00D">11</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span> <span style="color:#088;font-weight:bold">AUTO_INCREMENT</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">student_id</span><span style="color:#710">&quot;</span></span> <span style="color:#0a8;font-weight:bold">int</span>(<span style="color:#00D">11</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">public_pgp_key</span><span style="color:#710">&quot;</span></span> <span style="color:#0a8;font-weight:bold">text</span> <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">upload_date</span><span style="color:#710">&quot;</span></span> <span style="color:#0a8;font-weight:bold">datetime</span> <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">confirmation_date</span><span style="color:#710">&quot;</span></span> <span style="color:#0a8;font-weight:bold">datetime</span> <span style="color:#088;font-weight:bold">DEFAULT</span> <span style="color:#069">NULL</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">is_activated</span><span style="color:#710">&quot;</span></span> <span style="color:#0a8;font-weight:bold">tinyint</span>(<span style="color:#00D">1</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span> <span style="color:#088;font-weight:bold">DEFAULT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">0</span><span style="color:#710">'</span></span>, <span style="color:#088;font-weight:bold">PRIMARY</span> <span style="color:#339;font-weight:bold">KEY</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">id</span><span style="color:#710">&quot;</span></span>) ) <span style="color:#088;font-weight:bold">AUTO_INCREMENT</span>=<span style="color:#00D">1</span>; </pre></div> </div> </div> <p>oder graphisch:</p> <div style="width: 198px" class="wp-caption aligncenter"><a href="../images/2014/04/openpgp_keys.png"><img src="../images/2014/04/openpgp_keys.png" alt="openpgp_keys Tabelle" width="" height="" class="" /></a><p class="wp-caption-text">openpgp_keys Tabelle</p></div> <h3 id="ressourcen">Ressourcen</h3> <p>Sollte jemand den Vorschlag modifizieren wollen, hier ist das HTML dazu:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;div</span> <span style="color:#b48">class</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">content_full_portal</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;h1&gt;</span>PGP/GPG<span style="color:#070;font-weight:bold">&lt;/h1&gt;</span> <span style="color:#070;font-weight:bold">&lt;h2&gt;</span>Neuen Schlüssel hinzufügen<span style="color:#070;font-weight:bold">&lt;/h2&gt;</span> <span style="color:#070;font-weight:bold">&lt;div</span> <span style="color:#b48">style</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#606">width</span>: <span style="color:#60E">100%</span>;<span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;div</span> <span style="color:#b48">class</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">gwf3_formY</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;form</span> <span style="color:#b48">action</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">/account</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">method</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">post</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">enctype</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">multipart/form-data</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;table&gt;</span> <span style="color:#070;font-weight:bold">&lt;tbody&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span><span style="color:#070;font-weight:bold">&lt;td&gt;</span>Öffentlichen Schlüssel als Datei hochladen<span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;td&gt;</span> <span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;td&gt;</span><span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">file</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">gpg_file</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span><span style="color:#070;font-weight:bold">&lt;td</span> <span style="color:#b48">colspan</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">3</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>oder hier einfügen<span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span><span style="color:#070;font-weight:bold">&lt;td</span> <span style="color:#b48">colspan</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">3</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;textarea</span> <span style="color:#b48">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">gpg_paste</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">gpg_paste</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">cols</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">80</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">rows</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">8</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;/textarea&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span><span style="color:#070;font-weight:bold">&lt;td&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;td&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;td&gt;</span><span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">submit</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">setup_gpg</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">value</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Schlüssel hochladen</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span><span style="color:#070;font-weight:bold">&lt;td</span> <span style="color:#b48">colspan</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">3</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hidden</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">gwf3_csrf</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">value</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">gp1yqWh4</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span><span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;/tbody&gt;</span> <span style="color:#070;font-weight:bold">&lt;/table&gt;</span> <span style="color:#070;font-weight:bold">&lt;/form&gt;</span> <span style="color:#070;font-weight:bold">&lt;/div&gt;</span> <span style="color:#070;font-weight:bold">&lt;/div&gt;</span> <span style="color:#070;font-weight:bold">&lt;h2&gt;</span>Liste bekannter Schlüssel<span style="color:#070;font-weight:bold">&lt;/h2&gt;</span> <span style="color:#070;font-weight:bold">&lt;table</span> <span style="color:#b48">style</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#606">width</span>:<span style="color:#60E">100%</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;tbody&gt;</span><span style="color:#070;font-weight:bold">&lt;tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;th&gt;</span>Name des Schlüssels<span style="color:#070;font-weight:bold">&lt;/th&gt;</span> <span style="color:#070;font-weight:bold">&lt;th&gt;</span>Datum des Uploads<span style="color:#070;font-weight:bold">&lt;/th&gt;</span> <span style="color:#070;font-weight:bold">&lt;th&gt;</span>Bestätigt<span style="color:#070;font-weight:bold">&lt;/th&gt;</span> <span style="color:#070;font-weight:bold">&lt;th&gt;</span>Aktiviert<span style="color:#070;font-weight:bold">&lt;/th&gt;</span> <span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>sdfasdf asdfasd asdf<span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>12.10.2013, 14:45 Uhr<span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>am 12.10.2014, 16:00 Uhr<span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>Ja (<span style="color:#070;font-weight:bold">&lt;a</span> <span style="color:#b48">href</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>Deaktivieren<span style="color:#070;font-weight:bold">&lt;/a&gt;</span>)<span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>asdfasdf asdf asdfa sdf <span style="color:#800;font-weight:bold">&amp;nbsp;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>02.04.2014, 06:01 Uhr<span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span><span style="color:#070;font-weight:bold">&lt;a</span> <span style="color:#b48">href</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>noch nicht<span style="color:#070;font-weight:bold">&lt;/a&gt;</span><span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;td&gt;</span>Nein (<span style="color:#070;font-weight:bold">&lt;a</span> <span style="color:#b48">href</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>Aktivieren<span style="color:#070;font-weight:bold">&lt;/a&gt;</span>)<span style="color:#070;font-weight:bold">&lt;/td&gt;</span> <span style="color:#070;font-weight:bold">&lt;/tr&gt;</span> <span style="color:#070;font-weight:bold">&lt;/tbody&gt;</span><span style="color:#070;font-weight:bold">&lt;/table&gt;</span> <span style="color:#070;font-weight:bold">&lt;/div&gt;</span> </pre></div> </div> </div> <p>und</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;div</span> <span style="color:#b48">class</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">content_full_portal</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;h1&gt;</span>Prüfungsanmeldung<span style="color:#070;font-weight:bold">&lt;/h1&gt;</span> Signieren Sie folgende Nachricht mit ihrem Schlüssel:<span style="color:#070;font-weight:bold">&lt;br&gt;</span> <span style="color:#070;font-weight:bold">&lt;a</span> <span style="color:#b48">href</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>Nachricht als Textdatei herunterladen<span style="color:#070;font-weight:bold">&lt;/a&gt;</span><span style="color:#070;font-weight:bold">&lt;br&gt;</span> oder<span style="color:#070;font-weight:bold">&lt;br&gt;</span> Nachricht zum kopieren:<span style="color:#070;font-weight:bold">&lt;br&gt;</span> <span style="color:#070;font-weight:bold">&lt;textarea</span> <span style="color:#b48">style</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#606">width</span>: <span style="color:#60E">800px</span>;<span style="color:#606">height</span>: <span style="color:#60E">60px</span>;<span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>Hiermit melde ich, Martin Thoma (Matrikelnummer: 1612345), mich heute (28.03.2014, 12:34:56 Uhr) zur Prüfung 'Programmierparadigmen', die am 10.04.2014 statt findet, an. Mir ist bekannt, dass der letzte Zeitpunkt der Abmeldung am 08.04.2014 ist.<span style="color:#070;font-weight:bold">&lt;/textarea&gt;</span> <span style="color:#070;font-weight:bold">&lt;h2&gt;</span>Anmeldung durchführen<span style="color:#070;font-weight:bold">&lt;/h2&gt;</span> <span style="color:#070;font-weight:bold">&lt;form&gt;</span> <span style="color:#070;font-weight:bold">&lt;label</span> <span style="color:#b48">for</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">filet</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>Signierte Bestätigung als Textdatei hochladen:<span style="color:#070;font-weight:bold">&lt;/label&gt;</span><span style="color:#070;font-weight:bold">&lt;br&gt;</span> <span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">file</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">filet</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;br&gt;</span> <span style="color:#070;font-weight:bold">&lt;p&gt;</span>oder signierte Bestätigung direkt einfügen:<span style="color:#070;font-weight:bold">&lt;br&gt;</span><span style="color:#070;font-weight:bold">&lt;/p&gt;</span> <span style="color:#070;font-weight:bold">&lt;label</span> <span style="color:#b48">for</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">textareat</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;/label&gt;</span> <span style="color:#070;font-weight:bold">&lt;textarea</span> <span style="color:#b48">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">textareat</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">style</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#606">width</span>: <span style="color:#60E">800px</span>;<span style="color:#606">height</span>: <span style="color:#60E">60px</span>;<span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span><span style="color:#070;font-weight:bold">&lt;/textarea&gt;</span><span style="color:#070;font-weight:bold">&lt;br&gt;</span> <span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">submit</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;/form&gt;</span> <span style="color:#070;font-weight:bold">&lt;/div&gt;</span> </pre></div> </div> </div> <h2 id="weitere-probleme-der-prfungsorganisation">Weitere Probleme der Prüfungsorganisation</h2> <p>In diesem Artikel will ich nur die Prüfungsverwaltung diskutieren. Dennoch sollte darauf hingewiesen werden, dass Weiteres nicht gerade optimal gelöst ist:</p> <ul> <li><strong>Informationspolitik</strong>: Bereits zu Semesterbegin sollte folgendes bekannt sein: <ul> <li>Zeitpunkt der Prüfung</li> <li>Letztmöglicher Zeitpunkt der Anmeldung</li> <li>Letztmöglicher Zeitpunkt der Abmeldung</li> </ul> </li> <li>Die <strong>Anmeldungsfreischaltung</strong> der Prüfungen finden zu sehr unterschiedlichen Zeitpunkten statt. Die Anmeldung sollte breits zu Semesterbegin für alle Klausuren möglich sein.</li> <li>Die <strong>Einsicht</strong> ist immer schlecht organisiert. Da sich die Prüfungstermine größtenteils in der vorlesungsfreien Zeit befinden und darin aber stark gestreut sind (manche sind zu Beginn, manche in der Mitte, manche am Ende) sind die Zeitpunkte, zu denen man als Student Ferien hat sehr stark eingeschränkt. Wenn man dann erst nach der Klausur erfährt, wann die Einsicht sein wird, kann man Ferien komplett vergessen, weil man in Karlsruhe bleiben muss um auf den Termin der Einsicht zu warten.<br /> Bei den Physikern ist wenigstens die Korrektur immer sehr schnell, sodass man davon ausgehen kann, dass die Einsicht wenige Tage nach der Prüfung statt findet. Bei den Informatikern … naja, da hat man ja noch Glück wenn sie im selben Monat ist. Und man es dann rechtzeitig erfährt.</li> <li><strong>Lösungen und Notengrenzen</strong> sind nicht in jeder einsicht vorhanden bzw. klar. Gerade wenn nicht klar ist, mit welcher Punktzahl man welche Note bekommt könnte ein Fehler passieren, den man nicht überprüfen kann. Nach diesen Informationen sollte man nicht in der Einsicht fragen müssen. Sie sollten in der Einsicht direkt verfügbar sein.</li> </ul> <h2 id="schlusswort">Schlusswort</h2> <p>Welche Vorteile hat das beschriebene Verfahren gegenüber der momentanen Situation?</p> <ul> <li>Studenten können beweisen, dass sie zur Prüfung angemeldet sind / nicht sind</li> <li>Prüfer können beweise, dass Studenten angemeldet sind / nicht sind</li> </ul> <p>Selbst wenn man den Teil mit der asymmetrischen Verschlüsselung nicht macht, hätte man als Student zumindest ein bisschen was in der Hand und einen Mechanismus, der automatisch Feedback gibt, ob alles geklappt hat. Im Gegensatz zu der momentanen Situation, wo wir absolut nichts belegen können und man sehr leicht übersehen kann, wenn etwas bei der Anmeldung schief gegangen ist.</p> <p><strong>Was haltet ihr davon? Hattet ihr auch schon solche Probleme mit der Prüfungsanmeldung?</strong></p> Prolog //martin-thoma.com/prolog/ Wed, 02 Apr 2014 16:36:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/prolog <p>Prolog is a logic programming language.</p> <p>Any prolog program consists of</p> <ul> <li>declaration of facts (also called objects)</li> <li>rules about objects and their relationship</li> <li>asking “questions” about objects and their relationship</li> </ul> <h2 id="first-steps">First steps</h2> <p>At first you have to install <code>swi-prolog</code>. After installing it, you can call it with <code>swipl</code>.</p> <p>When you’ve started <code>swipl</code> you can import your myscript.pl files by <code>consult(myscript).</code>. Don’t forget the point at the end. It is important and somehow like the <code>;</code> in C.</p> <h2 id="defining-facts">Defining facts</h2> <p>The definition of facts can look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>loves(john,X). </pre></div> </div> </div> <ul> <li>Note that names of all relationships and all objects have to begin with a lower case letter. Variables begin with a capital letter.</li> <li>The relationship is written first (<code>john</code>). The objects are separated by <code>,</code> and everything is finished with <code>.</code>.</li> <li>The example from above means: <code>john</code> loves everything.</li> <li>You can have any number of arguments.</li> <li>The ordering of arguments is important (<code>loves(john,X)</code> is not the same as <code>loves(X,john)</code>).</li> </ul> <h3 id="symbols">Symbols</h3> <table> <thead> <tr> <th>Boolean</th> <th>Prolog</th> </tr> </thead> <tbody> <tr> <td>and</td> <td><code>,</code></td> </tr> <tr> <td>or</td> <td><code>;</code></td> </tr> <tr> <td>if</td> <td><code>:-</code></td> </tr> <tr> <td>not</td> <td><code>not</code></td> </tr> </tbody> </table> <ul> <li>An underscore <code>_</code> is an anonymous variable.</li> </ul> <h2 id="rules">Rules</h2> <p>Rules consist of a head and a body. They are separated by <code>:-</code>.</p> <h2 id="questions">Questions</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>?own(mary,book) </pre></div> </div> </div> <p>This will invoke the prolog unifier. So Prolog will check if the fact <code>own(mary,book)</code> can be derived from the known facts. Important is that it starts with <code>?</code>. Everything else in questions is just like it was for facts.</p> <h2 id="fox-goose-and-bag-of-beans-puzzle">Fox, goose and bag of beans puzzle</h2> <p>This puzzle helped me a lot to understand how Prolog works. It goes as follows:</p> <blockquote> <p>Once upon a time a farmer went to market and purchased a fox, a goose, and a bag of beans. On his way home, the farmer came to the bank of a river and rented a boat. But in crossing the river by boat, the farmer could carry only himself and a single one of his purchases - the fox, the goose, or the bag of the beans. If left together, the fox would eat the goose, or the goose would eat the beans. The farmer’s challenge was to carry himself and his purchases to the far bank of the river, leaving each purchase intact. How did he do it?</p> </blockquote> <p>Source: <a href="https://en.wikipedia.org/wiki/Fox,_goose_and_bag_of_beans_puzzle">Wikpedia</a></p> <p>Let’s call the side of the river where the farmer currently is ‘left’ and the other side ‘right’ to make things easier.</p> <p>When you solve this by hand, you should note the following:</p> <ul> <li>The only two things that the farmer can leave alone is the fox and the bag of beans.</li> <li>As the farmer is always in the boat when anything else is in the boat, you can ignore that step. Just think of the farmer and possibly one other thing teleporting from one side to the other.</li> <li>You only have to look at what’s left and what’s right. If nothing gets eaten on the left side and nothing gets eaten on the right side, you’ve got a valid situation.</li> <li>Whenever a situation occurs twice, you did some redundant steps. In other words: At least one solution exists, where no repetitions take place. The shortest solution is one of them.</li> </ul> <p>To solve this task, you split the problem into parts:</p> <ul> <li>Define a rule <code>valid</code> that takes a 4-tuple, where the first element is the position of the man, the second of the goose, then the fox and then the beans. Positions can either be <code>left</code> or <code>right</code>.</li> <li>Define a rule <code>step(S1, Description, S2)</code> that makes one step from situation <code>S1</code> to situation <code>S2</code> where <code>Description</code> contains the information what was brought to the other side. The situations are, as above, 4-tuples.</li> <li>Define a rule <code>reachable(S1, SituationList, Steps, S2)</code> that is true if <code>S2</code> can be reached by any number of steps from <code>S1</code>. The list of steps done to get from <code>S1</code> to <code>S2</code> is stored in <code>Steps</code>. The <code>SituationList</code> is used to prevent doing unnecessary redundant steps.</li> </ul> <p>So lets get through this.</p> <p>There are essentially three situations that can occur:</p> <ul> <li>The man is on the same side as the goose,</li> <li>the man is on the same side as the beans or</li> <li>the man is on the same side as the fox.</li> </ul> <p>If the man is on the same side as the goose, everything is fine. Nobody gets eaten / eats when the man is there.</p> <p>If the man is where the beans are, then the goose should not be where the fox is. The case that the goose is where the man is was done before.</p> <p>And the last case, the man is where the fox is. Now we have to make sure that the beans are not where the goose is:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>p(left). p(right). valid((Man, Goose, Fox, Beans)) :- p(Man),p(Goose),p(Fox),p(Beans), Man == Goose. valid((Man, Goose, Fox, Beans)) :- p(Man),p(Goose),p(Fox),p(Beans), Man == Beans, Goose \= Fox. valid((Man, Goose, Fox, Beans)) :- p(Man),p(Goose),p(Fox),p(Beans), Man == Fox, Goose \= Beans. </pre></div> </div> </div> <p>The <code>step</code> is also quite simple. There are four possible actions you could take at each situation:</p> <ul> <li>Only the man goes to the other side,</li> <li>the man and the beans / goose / fox go the the other side.</li> </ul> <p>So here is the code:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>step((Man1, Goose, Fox, Beans), 'Man', (Man2, Goose, Fox, Beans)) :- Man1 \= Man2. step((Man1, Goose1, Fox, Beans), 'Goose', (Man2, Goose2, Fox, Beans)) :- Man1 \= Man2, Goose1 \= Goose2. step((Man1, Goose, Fox1, Beans), 'Fox', (Man2, Goose, Fox2, Beans)) :- Man1 \= Man2, Fox1 \= Fox2. step((Man1, Goose, Fox, Beans1), 'Beans', (Man2, Goose, Fox, Beans2)) :- Man1 \= Man2, Beans1 \= Beans2. </pre></div> </div> </div> <p>And finally the reachable part.</p> <ul> <li>Either, you’re already at the situation where you want to get to. So you don’t have to do any step and it doesn’t matter which situations you have seen so far.</li> <li>Or you want to get from <code>S</code> to <code>G</code>. That is only possible, when you can get from <code>S</code> to an intermediate situation with one step less:</li> </ul> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>reachable(S, _, [], S). reachable(S, Visited, [Step|Steps], G) :- step(S, Step, Tmp), valid(Tmp), not(member(Tmp, Visited)), reachable(Tmp, [Tmp|Visited], Steps, G). </pre></div> </div> </div> <p>Putting it together:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>p(left). p(right). valid((Man, Goose, Fox, Beans)) :- p(Man),p(Goose),p(Fox),p(Beans), Man == Goose. valid((Man, Goose, Fox, Beans)) :- p(Man),p(Goose),p(Fox),p(Beans), Man == Beans, Goose \= Fox. valid((Man, Goose, Fox, Beans)) :- p(Man),p(Goose),p(Fox),p(Beans), Man == Fox, Goose \= Beans. step((Man1, Goose, Fox, Beans), 'Man', (Man2, Goose, Fox, Beans)) :- valid((Man2, Goose, Fox, Beans)), Man1 \= Man2. step((Man1, Goose1, Fox, Beans), 'Goose', (Man2, Goose2, Fox, Beans)) :- valid((Man2, Goose2, Fox, Beans)), Man1 \= Man2, Goose1 \= Goose2. step((Man1, Goose, Fox1, Beans), 'Fox', (Man2, Goose, Fox2, Beans)) :- valid((Man2, Goose, Fox2, Beans)), Man1 \= Man2, Fox1 \= Fox2. step((Man1, Goose, Fox, Beans1), 'Beans', (Man2, Goose, Fox, Beans2)) :- valid((Man2, Goose, Fox, Beans2)), Man1 \= Man2, Beans1 \= Beans2. reachable(S, _,[], S). reachable(S, Visited, [Step|Steps], G) :- step(S, Step, Tmp), not(member(Tmp, Visited)), reachable(Tmp, [Tmp|Visited], Steps, G). start((left,left,left,left)). goal((right,right,right,right)). solve(Steps) :- start(S), goal(G), reachable(S, [], Steps, G). </pre></div> </div> </div> <p>You can load this with <code>swipl -s puzzle.pl</code> and get all solutions with <code>bagof(X, solve(T), L)</code>. When you press <code>;</code> after the first solution, you get the second solution. (Yes, this riddle has only two solutions that avoid redundant steps.)</p> <h2 id="material">Material</h2> <ul> <li><a href="http://www.youtube.com/watch?v=GHLfeGN5OMk">Introduction to PROLOG</a>: One hour of introduction to prolog by Shashi Bhushan. Much of what I have written here is based on this video.</li> <li><a href="http://www.swi-prolog.org/">SWI Prolog</a>: A great resource for looking things up.</li> <li><a href="http://www.cs.trincoll.edu/~ram/cpsc352/notes/prolog/factsrules.html">Facts, Rules and Queries</a></li> <li><a href="http://www.cs.toronto.edu/~hojjat/384w09/simple-prolog-examples.html">Simple Prolog example</a></li> </ul> TCL //martin-thoma.com/tcl/ Wed, 02 Apr 2014 04:04:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/tcl <p>TCL is an imperative, interpreted, dynamically typed programming language. The <strong>T</strong>ool <strong>C</strong>ommand <strong>L</strong>anguage appeared in 1988. In Tcl, everything is a string.</p> <p>It is probably best (and completely?) described by the <a href="../tcl-12-rules.html">12 Rules for Tcl</a>.</p> <h2 id="basic-syntax-by-example">Basic Syntax by Example</h2> <p>Some nice comparisons of the syntax of many languages can be found at <a href="http://rigaux.org/language-study/syntax-across-languages.html">rigaux.org</a></p> <h3 id="hello-world">Hello World</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>set myVariable &quot;Hallo World!&quot; puts $myVariable </pre></div> </div> </div> <h3 id="loop-over-a-list">Loop over a list</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>% foreach element {1 2 3} { puts $element } </pre></div> </div> </div> <h3 id="fibonacci">Fibonacci</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>proc fib {n} { if {$n &lt; 2} { return $n } else { return [expr {[fib [expr {$n-2}]] + [fib [expr {$n-1}]]}] } } for {set x 0} {$x&lt;10} {incr x} { puts [fib $x] } </pre></div> </div> </div> <h3 id="comments">Comments</h3> <p>TCL uses <code>#</code> as a line comment and does not offer block comments. In fact, they recommend this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>if 0 { Any Tcl code to be commented out (with matching braces, of course!) or any other kind of text, will be ignored - and even [exit] won't fire because it's in braces, so left unevaluated! } </pre></div> </div> </div> <p>Source: <a href="http://wiki.tcl.tk/1669">wiki.tcl.tk/1669</a></p> <h3 id="logical-operators">Logical operators</h3> <table> <thead> <tr> <th>AND</th> <th>OR</th> <th>TRUE</th> <th>FALSE</th> </tr> </thead> <tbody> <tr> <td>&amp;&amp;</td> <td>||</td> <td>1</td> <td>0</td> </tr> <tr> <td><strong>EQUAL</strong></td> <td><strong>UNEQUAL</strong></td> <td><strong>NOT</strong></td> <td> </td> </tr> <tr> <td>==</td> <td>!=</td> <td>!</td> <td> </td> </tr> </tbody> </table> <h3 id="bottles-of-beer">99 bottles of beer</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>#!/usr/bin/tclsh # 99.tcl; Tcl version of 99 Bottles of Beer Song proc findBString { count } { return [switch -exact -- $count { 0 { expr {&quot;No more bottles&quot;} } 1 { expr {&quot;1 bottle&quot;} } default { expr {&quot;$count bottles&quot;} } }] } set bottles 99 set bString [findBString $bottles] while {$bottles + 1} { puts &quot;$bString of beer on the wall. $bString of beer.&quot; incr bottles -1 if {$bottles + 1} { set bString [findBString $bottles] puts &quot;Take one down, pass it round, $bString of beer on the wall.\n&quot; } else { puts &quot;Go to the store and buy some more...99 bottles of beer.&quot; } } </pre></div> </div> </div> <p>Source: <a href="http://99-bottles-of-beer.net/language-tcl-797.html">99-bottles-of-beer.net</a></p> <h3 id="argument-parsing">Argument parsing</h3> <p>See <a href="http://www.cs.cmu.edu/~tanja/Lectures/JRTkDoc/OldDoc/interface/parseArgv.html"><code>itfParseArgv</code></a></p> <h2 id="naming-schemes">Naming schemes</h2> <ul> <li>Variables have to fit to the pattern <code>[_a-zA-Z][_a-zA-Z0-9]*</code>.</li> <li>Functions have to fit to the pattern <code>[^ \t\n\r\f]+</code>.</li> <li>Variables and function are scrunched together by camelCase or CamelCase.</li> </ul> <h2 id="community">Community</h2> <p>I think one indicator for the quality of the community is it’s size. And the community will grow, when the language gets more popular.</p> <p>According to <a href="http://www.ohloh.net/languages/compare">Ohloh</a>, TCL is quite unpopular:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/04/monthly-commits-ohloh.png" class="image"><img src="//martin-thoma.com/captions/monthly-commits-ohloh.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Monthly Commits</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/04/monthly-contributors-ohloh.png" class="image"><img src="//martin-thoma.com/captions/monthly-contributors-ohloh.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Monthly Contributors</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/04/monthly-loc-ohloh.png" class="image"><img src="//martin-thoma.com/captions/monthly-loc-ohloh.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Monthly Lines of Code</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/04/monthly-projects-ohloh.png" class="image"><img src="//martin-thoma.com/captions/monthly-projects-ohloh.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Monthly Projects</div></div></li></ul> <p>You can also take a look at <a href="http://www.google.com/trends/">Google Trends</a>:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/04/google-trends-tcl.png"><img src="//martin-thoma.com/captions/google-trends-tcl.png" alt="Google Trends" width="500" height="198" class="" /></a><p class="wp-caption-text">Google Trends</p></div> <ul> <li>The <a href="http://www.tiobe.com/index.php/content/paperinfo/tpci/index.html">TIOBE Index</a> ranked Tcl on place 43 in March 2014.</li> <li><a href="http://lang-index.sourceforge.net/">lang-index</a> ranked Tcl on place 84 in the general category and on place 34 in the script category.</li> <li>There are 2,490 Tcl questions on StackOverflow. Compare that to 286,244 questions about Python or 609,648 questions about Java.</li> <li>Tcl is on rank 18 for GitHub (<a href="http://adambard.com/blog/top-github-languages-for-2013-so-far/">source</a>).</li> </ul> <h2 id="execution-speed">Execution Speed</h2> <p>Speed comparisons of programming languages are difficult. One nice way to compare the execution speed of programming languages is the <a href="http://benchmarksgame.alioth.debian.org/">benchmarksgame</a>. But sadly, they don’t have TCL.</p> <h2 id="additional-information">Additional information</h2> <ul> <li><a href="http://www.tcl.tk/">Official website</a></li> <li><a href="https://en.wikipedia.org/wiki/Tcl">Wikipedia</a></li> </ul> Panasonic Lumix DMC-TZ41 //martin-thoma.com/panasonic-lumix-tz41/ Thu, 27 Mar 2014 22:31:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/panasonic-lumix-tz41 <div style="width: 138px" class="wp-caption alignright"><a href="../images/2014/03/panasonic-lumix-tz41.jpg"><img src="//martin-thoma.com/captions/panasonic-lumix-tz41-2.jpg" alt="Panasonic Lumix TZ41" width="128" height="76" class="" /></a><p class="wp-caption-text">Panasonic Lumix TZ41</p></div> <p>The <span itemprop="name">Panasonic Lumix TZ41</span> is currently the best camera in the compact segment.</p> <p><span itemprop="description">The TZ41 offers an excellent 20× zoom that is usable due to optical image stabilization. It is compact, leightweight and has a reasonably-sized battery.</span></p> <h2 id="technical-specification">Technical specification</h2> <table> <thead> <tr> <th>Name</th> <th>Panasonic Lumix TZ41</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>Panasonic DMC-TZ41EG-K</td> </tr> <tr> <td>Price</td> <td><span itemprop="offers" itemscope="" itemtype="http://schema.org/Offer"><span itemprop="price">259.03</span> <span itemprop="priceCurrency">Euro</span></span></td> </tr> <tr> <td>Dimensions</td> <td>108.3 × 58.9 × 27.7 mm</td> </tr> <tr> <td>Weight</td> <td>198g</td> </tr> <tr> <td>Zoom</td> <td>20×</td> </tr> <tr> <td>optical image stabilization</td> <td>✔</td> </tr> <tr> <td>Battery Power</td> <td>1250mAh</td> </tr> <tr> <td>GPS Sensor</td> <td>✔</td> </tr> <tr> <td>Sensor</td> <td>1/2.3” MOS Sensor with 18.9 Megapixel</td> </tr> <tr> <td>Video</td> <td>1920 x 1080 full HD video</td> </tr> <tr> <td>Wi-Fi</td> <td>✔</td> </tr> <tr> <td>NFC</td> <td>✔</td> </tr> <tr> <td>LCD Monitor</td> <td>✔</td> </tr> <tr> <td>Internal Storage</td> <td>12 MB</td> </tr> </tbody> </table> <p>This camera is the same as the ‘<span itemprop="alternateName">TZ40</span>’ which has an <a href="http://www.panasonic.com/au/consumer/imaging/lumix-cameras/dmc-tz40.specs.html"><span itemprop="sameAs">official data sheet</span></a> and <a href="http://www.digitalkamera.de/Kamera/Panasonic/Lumix_DMC-TZ41.aspx">digitalkamera.de</a>.</p> <h3 id="model-name">Model name</h3> <table> <thead> <tr> <th>Panasonic</th> <th>Meaning</th> <th>Alternatives</th> </tr> </thead> <tbody> <tr> <td><a href="https://en.wikipedia.org/wiki/Lumix">Lumix</a></td> <td>Compact cameras</td> <td> </td> </tr> <tr> <td>DMC</td> <td><a href="http://photo.stackexchange.com/q/49043/27076">Digital Media Camera</a></td> <td> </td> </tr> <tr> <td>TZ</td> <td>Traveler Zoom</td> <td>SZ, TS, GM, LX</td> </tr> <tr> <td>41</td> <td> </td> <td>40 seems to be the same as 41; 60, …</td> </tr> <tr> <td>EG</td> <td>European Union model</td> <td> </td> </tr> <tr> <td>K</td> <td>Black colored</td> <td>W = White, R = Red, S = Silver</td> </tr> </tbody> </table> <h2 id="critic">Critic</h2> <h3 id="charger">Charger</h3> <p>Panasonic doesn’t use the standard european charger / cable combination that is used for smartphones.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/panasonic-lumix-tz-41-charger.jpg"><img src="//martin-thoma.com/captions/panasonic-lumix-tz-41-charger.jpg" alt="Loading works via microUSB, but not via standard charger." width="500" height="458" class="" /></a><p class="wp-caption-text">Loading works via microUSB, but not via standard charger.</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/panasonic-cable-standard-cable.jpg"><img src="//martin-thoma.com/captions/panasonic-cable-standard-cable.jpg" alt="Panasonic does not use standard microUSB2USB cables for charging / data exchange" width="500" height="318" class="" /></a><p class="wp-caption-text">Panasonic does not use standard microUSB2USB cables for charging / data exchange</p></div> <h3 id="software">Software</h3> <p>The software is not available for Linux.</p> <h2 id="linux">Linux</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc08$ cat /etc/issue Linux Mint 16 Petra moose@pc08$ uname -a Linux pc08 3.11.0-12-generic #19-Ubuntu SMP Wed Oct 9 16:20:46 UTC 2013 x86_64 x86_64 x86_64 GNU/Linux </pre></div> </div> </div> <p>and the camera as a USB device:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc08$ lsusb Bus 001 Device 006: ID 04da:2372 Panasonic (Matsushita) Lumix Camera (Storage mode) </pre></div> </div> </div> <h3 id="gps-assist-tool">GPS Assist Tool</h3> <p>The GPS Assist Tool seems to update the camera internal GPS information. It works like this:</p> <ol> <li>Connect camera with SD card in it to the computer.</li> <li>Start gpsasist.exe with wine.</li> </ol> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/gpsasist.exe.png" class="image"><img src="//martin-thoma.com/captions/gpsasist.exe.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">gpsasist.exe</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/gps-assist-tool.png" class="image"><img src="//martin-thoma.com/captions/gps-assist-tool.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">gps-assist-tool</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/gps-update-completed.png" class="image"><img src="//martin-thoma.com/captions/gps-update-completed.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">update completed</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/gps-assist-settings.png" class="image"><img src="//martin-thoma.com/captions/gps-assist-settings.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Settings</div></div></li></ul> <h3 id="lumix-map-tool">LUMIX Map Tool</h3> <p>The LUMIX Map Tool should allow you to copy maps with information about the environment on your camera. It looks like this:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/lumix-map-tool.png" class="image"><img src="//martin-thoma.com/captions/lumix-map-tool.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/lumix-map-tool-no-drive-detection.png" class="image"><img src="//martin-thoma.com/captions/lumix-map-tool-no-drive-detection.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <p>The drive detection for the SD card doesn’t work on Linux as you can see in the second image. So I’ve have written a Linux version of that program which can be found on <a href="https://github.com/MartinThoma/lumix_map_tool">GitHub</a>.</p> <h2 id="example-photographs">Example photographs</h2> <p>To compare the quality of the Panasonic Lumix DMC-TZ41 I have shot some photographs with my old Casio Lumix Exilim EX-Z200.</p> <h3 id="macro-photographs">Macro photographs</h3> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/blume-blau-1.jpg" class="image"><img src="//martin-thoma.com/captions/blume-blau-1.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/blume-blau-1.jpg" class="image"><img src="//martin-thoma.com/captions/blume-blau-1-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/blume-glare.jpg" class="image"><img src="//martin-thoma.com/captions/blume-glare.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li></ul> <h3 id="normal-range-photographs">Normal range photographs</h3> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/bank.jpg" class="image"><img src="//martin-thoma.com/captions/bank.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/bank.jpg" class="image"><img src="//martin-thoma.com/captions/bank-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/blume-front-unschaerfe.jpg" class="image"><img src="//martin-thoma.com/captions/blume-front-unschaerfe.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/blume-front-unschaerfe.jpg" class="image"><img src="//martin-thoma.com/captions/blume-front-unschaerfe-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/schlossplatz.jpg" class="image"><img src="//martin-thoma.com/captions/schlossplatz.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/schlossplatz.jpg" class="image"><img src="//martin-thoma.com/captions/schlossplatz-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/springbrunnen-ganz.jpg" class="image"><img src="//martin-thoma.com/captions/springbrunnen-ganz.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/springbrunnen-ganz.jpg" class="image"><img src="//martin-thoma.com/captions/springbrunnen-ganz-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li></ul> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/relief.jpg" class="image"><img src="//martin-thoma.com/captions/relief.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/poor-light-conditions.jpg" class="image"><img src="//martin-thoma.com/captions/poor-light-conditions.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/taube-fliegt.jpg" class="image"><img src="//martin-thoma.com/captions/taube-fliegt.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/enterich-1.jpg" class="image"><img src="//martin-thoma.com/captions/enterich-1.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/enterich-2.jpg" class="image"><img src="//martin-thoma.com/captions/enterich-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/enterich-3.jpg" class="image"><img src="//martin-thoma.com/captions/enterich-3.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/enterich-4.jpg" class="image"><img src="//martin-thoma.com/captions/enterich-4.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/ente-1.jpg" class="image"><img src="//martin-thoma.com/captions/ente-1.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/ente-2.jpg" class="image"><img src="//martin-thoma.com/captions/ente-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/ente-und-enterich-1.jpg" class="image"><img src="//martin-thoma.com/captions/ente-und-enterich-1.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/ente-und-enterich-2.jpg" class="image"><img src="//martin-thoma.com/captions/ente-und-enterich-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/fassade.jpg" class="image"><img src="//martin-thoma.com/captions/fassade.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/fassade-statue.jpg" class="image"><img src="//martin-thoma.com/captions/fassade-statue.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/springbrunnen.jpg" class="image"><img src="//martin-thoma.com/captions/springbrunnen.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext"></div></div></li></ul> <h3 id="long-range-photographs">Long-range photographs</h3> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/ente-zoom.jpg" class="image"><img src="//martin-thoma.com/captions/ente-zoom.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/ente-zoom.jpg" class="image"><img src="//martin-thoma.com/captions/ente-zoom-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/schlosstor-zoom.jpg" class="image"><img src="//martin-thoma.com/captions/schlosstor-zoom.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/schlosstor-zoom.jpg" class="image"><img src="//martin-thoma.com/captions/schlosstor-zoom-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/casio-exilim-ex-z200/schloss-zoom-spitze.jpg" class="image"><img src="//martin-thoma.com/captions/schloss-zoom-spitze.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Casio</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/03/panasonic-lumix-dmc-tz-41/schloss-zoom-spitze.jpg" class="image"><img src="//martin-thoma.com/captions/schloss-zoom-spitze-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">TZ41</div></div></li></ul> <h2 id="conclusion">Conclusion</h2> <p>Overall, the Panasonic Lumix TZ41 is a great camera. But the lack of a standard charger and a standard cable as well as the missing Linux software is a downer. This is the reason why <meta itemprop="author" property="v:reviewer" content="Martin Thoma" />I <span itemprop="reviewRating" rel="v:rating" itemscope="" itemtype="http://schema.org/Rating"></span></p> <meta itemprop="worstRating" content="1" property="v:worst" /> <p>give it <span itemprop="ratingValue" property="v:rating">4</span>/<span itemprop="bestRating" property="v:best">5</span> stars.&lt;/span&gt;</p> <h2 id="more-information">More Information</h2> <p>Good German resources are:</p> <ul> <li><a href="http://www.chip.de/artikel/Panasonic-Lumix_DMC-TZ41-Digitalkamera-Test_60063203.html">Chip.de</a>: A review with some comparisons to other cameras.</li> <li><a href="https://www.youtube.com/watch?v=4v2vLMihcOg">Panasonic Lumix DMC-TZ41 - Mein Fazit</a>: A very detailed video review.</li> </ul> Project Glooseberry //martin-thoma.com/project-glooseberry/ Tue, 25 Mar 2014 12:32:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/project-glooseberry <p>Blender is an open source software that allows you to create animations. The <a href="https://en.wikipedia.org/wiki/Blender_Foundation">Blender Foundation</a> is a non-profit organization that helps to develop blender.</p> <p>To improve Blender, they have created movies. In that process, developers and movie makers sat in one room. So when the movie makers had a problem or discovered a bug, the developers could see and eventually fix that.</p> <p>By now, they have create four short movies. These movies are DRM-free, free to use and … well, you can basically do what you want with them:</p> <iframe width="560" height="315" src="//www.youtube.com/embed/YE7VzlLtp-4?list=PL6B3937A5D230E335" frameborder="0" allowfullscreen=""></iframe> <p><a href="http://gooseberry.blender.org/">Project Glooseberry</a> is an attempt to create a full length movie. Here is a first trailer:</p> <iframe width="560" height="315" src="//www.youtube.com/embed/XfezG5M2ICg" frameborder="0" allowfullscreen=""></iframe> <p>But creating movies is quite cost intensive. A lot of people are involved and a lot of processing power is needed to create those animations. So the Blender Foundation has started a <a href="https://cloud.blender.org/gooseberry/pledge">Crowdfunding Campaign</a>.</p> <ul> <li>You can pledge what you want. I’ve pledged 5 Euros.</li> <li>When you pay via PayPal and they don’t manage to get the 500 000 Euro they aim for, you get your money back.</li> <li>The campaign ends on April 19th 2014.</li> </ul> <h2 id="current-campaign-status">Current campaign status</h2> <p>You can see the current campaign status <a href="http://gooseberry.blender.org/#stats">here</a>.</p> <p>By now (25th of March, 13:37) there are 809 people that supported this campaign and 65,780 Euro were pledged.</p> <p>Let me know in comments when you supported the campaing: <a href="https://cloud.blender.org/gooseberry/pledge">support now</a>.</p> How to use Sublime Text via SSH //martin-thoma.com/sublime-via-ssh/ Thu, 20 Mar 2014 21:09:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sublime-via-ssh <p>Sublime Text is the best editor I have ever used. One argument for vim and against SSH could be that you can’t simply use Sublime Text when you’re accessing a computer via SSH. But there is a way!</p> <p>In the following, I will expain the simplest way how to remote edit files with Sublime Text.</p> <h2 id="preparation-on-your-computer">Preparation on your computer</h2> <ol> <li>Install and start Sublime Text.</li> <li>Install the <code>rsub</code> package via Package Controll.</li> <li>Open <code>~/.ssh/config</code>. Create it if id does not exist yet. Add the code from below.</li> <li>Start SSH with <code>ssh myname</code>.</li> </ol> <p>This is how the <code>config</code> file should look like:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Host myname Hostname pc123.your.network.com RemoteForward 52698 127.0.0.1:52698 </pre></div> </div> </div> <p>You can add more information like <code>User yourusername</code> to this file.</p> <h2 id="server-side-steps">Server-Side steps</h2> <ol start="5"> <li>Download the <code>rmate</code> script:<br /> <code>curl https://raw.github.com/aurora/rmate/master/rmate &gt; rmate</code> </li> <li>Execute <code>./rmate yourfile</code>. It will open in your local Sublime Text!</li> </ol> <h2 id="improvements">Improvements</h2> <p>These steps have to be done server-side.</p> <h3 id="with-root-access">With Root access</h3> <p>It’s not so nice to open files with <code>~/rmate filename</code> all the time. You can use <code>rmate filename</code> after executing this command:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># This creates a symlink sudo ln -s ~/rmate /usr/local/bin/ </pre></div> </div> </div> <p>You can use other paths than <code>/usr/local/bin/</code>. Look at your <code>PATH</code> for candidates:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>echo $PATH </pre></div> </div> </div> <h3 id="without-root-access">Without Root access</h3> <p>When you don’t have root access, you can’t create a symlink for most (eventually even all) folders in your <code>PATH</code>. But you can expand your <code>PATH</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>mkdir -p ~/bin # create folder if it doesn't exist ln -s ~/rmate ~/bin/ # create symlink </pre></div> </div> </div> <p>Now expand your <code>PATH</code> so that it includes <code>~/bin</code>. There are at least two ways to do so:</p> <ul> <li>You can directly edit your shells <code>.rc</code> file (e. g. <code>.bashrc</code>, <code>.zshrc</code>, <code>.cshrc</code>, …) or</li> <li>you can edit your <code>.profile</code></li> </ul> <p>As many shells source <code>.profile</code> I’ll explain this way. First, open <code>~/.profile</code>. Then add</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># First check if that folder exists if [ -d &quot;$HOME/bin&quot; ] ; then # Add your home folder to the end of the current path PATH=&quot;$PATH:$HOME/bin&quot; fi </pre></div> </div> </div> Interpreters and Shells //martin-thoma.com/interpreters-and-shells/ Sat, 08 Mar 2014 11:49:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/interpreters-and-shells <p>Should you ever be in the position to write a shell or interpreter I hope you will make sure the following things work. Take it as a quality guide. They are ordered by level of importance. The first thing is the most basic one that has to work, the last one is less necessary, but much cooler if you support it.</p> <p>In the following, I’ll only talk about shells. But most of it will also apply to interpreters.</p> <h2 id="level-0-robustness">Level 0: Robustness</h2> <p>A shell has to be robust. Users rely on it when GUI doesn’t work. This means it should definitely not fail. Never.</p> <p>And just to make sure that you get me correct. Commands get “Entered”. So the user pushes “enter” when he wants something to happen. Everything the shell does meanwhile should not change the system (except for shell-related stuff) and not be able to slow down / crash the system.</p> <h2 id="level-1-speed">Level 1: Speed</h2> <p>I expect a shell to start without recognizable delay. I’m not too sure how fast ‘without recognizable delay’ means. In the most extreme case it would be about 1/100 of a second, because when monitors have 100Hz they are said to be flicker free. You could not even see that. But I think it is not necessary.</p> <p>Another measure would be reaction time. I’ve just did an online test and saw that my reaction time is about 0.2 seconds. So a shell should be ready for user input after this time.</p> <h2 id="level-2-left--right-arrow-keys">Level 2: Left / Right arrow keys</h2> <p>When I enter a command, it happens that I forget something. In this case I want to be able to navigate with left / right arrow keys through the console.</p> <h2 id="level-3-history-with-up--down-arrow-keys">Level 3: History with up / down arrow keys</h2> <p>When you use the up-array, you should get the last command you’ve entered. When you press it twice, you get the second last command… So the shell should save your last commands in a so called “history”. This history should be at least</p> <h2 id="level-4-customization">Level 4: Customization</h2> <ul> <li>Promt</li> <li>History length</li> </ul> <h2 id="level-5-path-autocompletion">Level 5: Path autocompletion</h2> <p>The path should autocomplete when you hit <kbd>Tab</kbd>. The autocomplete should work as follows:</p> <ol> <li>The autocomplete should never get farer than one folder.</li> <li>If there are multiple possibilities to autocomplete, then it should only autocomplete what is in common. After a second <kbd>Tab</kbd> it should display the possibilities and after a third <kbd>Tab</kbd> the shell should go to the first possibility so that you can hit enter to use this possibility.</li> </ol> <h2 id="level-6-command-autocompletion">Level 6: Command autocompletion</h2> <p>The autocomplete function should also complete commands.</p> <h2 id="level-7-fuzzy-autocompletion">Level 7: Fuzzy autocompletion</h2> <p>When you make a typo in a path and hit <kbd>Tab</kbd> the shell should correct the typo if possible.</p> <h2 id="additional-stuff">Additional stuff</h2> <p>Some stuff is nice to have, but not really essential:</p> <ul> <li>Some default commands like <code>help</code>, <code>time</code>, <code>pwd</code>, <code>cd</code> and <code>echo</code>.</li> <li><kbd>Ctrl</kbd> + <kbd>D</kbd> as a shortcut for exiting.</li> <li><kbd>Ctrl</kbd> + <kbd>C</kbd> should stop the current command.</li> <li>The configuration file should be stored in the home folder of the user and it should be called <code>.[name]rc</code>. The dot makes the file invisible by convention and ‘rc’ means ‘resource configuration’.</li> <li>The prompt configuration should be easy. Some patterns that are used quite often are <ul> <li><code>\w</code> for the working directory, where ``$HOME<code> gets abbreviated with </code>~`</li> <li><code>\u</code> the username</li> <li><code>\h</code> the hostname</li> <li>Using colors for different parts</li> </ul> </li> <li>Navigation with <kbd>Pos 1</kbd> and <kbd>End</kbd> should work.</li> </ul> <h2 id="ranking">Ranking</h2> <p>Here is how some shells rank. Please note, that it’s very difficult to check if a shell is robust. :</p> <p><strong>Level 0</strong>: Windows XP / Windows 7 default shell; Windows Power shell<br /> The shell is too slow. I don’t know if this is still a problem in Windows 8, but I guess so.</p> <p>The <code>scala</code> interactive interpreter is slow.</p> <p><strong>Level 1</strong>: <code>csh</code> prints “^[[D” when I press the left arrow and “^[[C” when I press the right arrow. When I press <kbd>Tab</kbd> it only prints tab. What a crap.</p> <p><strong>Level 3</strong>: <code>python</code> seems to have possibilities to execute arbitrary python code at startup by specifying the environment variable <code>PYTHONSTARTUP</code>, but somehow this does not work on my system.<br /> However, customizing the prompt is fairly easy:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">sys</span> sys.ps1 = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--&gt;</span><span style="color:#710">&quot;</span></span> </pre></div> </div> </div> <p><strong>Level 4</strong>: <code>GHCi</code>, a Haskell compiler, has mastered level 4. The prompt can be configured via <code>~/.ghci</code> by adding <code>:set prompt "ghci&gt; "</code>.</p> <p>If you want to show the current path, you can do it like this (<a href="http://stackoverflow.com/a/11263118/562769">source</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>let cur fill = do { cwd &lt;- System.Directory.getCurrentDirectory; return (&quot;:set prompt \&quot;&quot; ++ cwd ++ fill ++ &quot; \&quot;&quot;); } :def doprompt (\_ -&gt; cur &quot;&gt;&quot;) :def mycd (\dir -&gt; System.Directory.setCurrentDirectory dir &gt;&gt; cur &quot;&gt;&quot;) :doprompt </pre></div> </div> </div> <p><strong>Level 4.5</strong>: <code>bash</code> is robust, takes about 0.11 seconds to start, has a history of 500 lines as you can verify with <code>echo $</code>HISTSIZE<code>, is customizable with </code>.bashrc`.</p> <p><code>tcsh</code> takes about 0.02 seconds to start, has a default history size of 100 lines as you can verify with <code>echo $history</code>, is customizable with <code>.tcshrc</code> and <code>.cshrc</code>.</p> <p>Rubys interactive interpreter <code>irb</code> seems to be fast enough, has a history, the prompt can be configured in <code>~/.riplrc</code> (<a href="http://stackoverflow.com/a/6097629/562769">source</a>). I don’t know if the history length is limited and can be adjusted.</p> <p>All shells in this level have path autocompletion as described in 5.1, but do not have autocompletion as described in 5.2.</p> <p><strong>Level 7</strong>: ZSH is the best shell I have ever used. Especially with <a href="https://github.com/robbyrussell/oh-my-zsh">oh-my-zsh</a>.</p> <h2 id="additional-resources">Additional resources</h2> <ul> <li><a href="http://www.understudy.net/custom.html">How to change your shell prompt</a>: A list of files and commands that might be useful.</li> </ul> Internet at KIT //martin-thoma.com/internet-at-kit/ Thu, 06 Mar 2014 11:35:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/internet-at-kit <p>This article is about how to get internet at KIT with Linux. It was tested on Linux Mint 16 MATE which is based on Ubuntu which is based on Debian.</p> <h2 id="wlan">WLAN</h2> <p>At KIT are a lot of WLANs, but only two are important: <code>wkit-802.1x</code> and <code>eduroam</code>.</p> <ul> <li>Mode: Infrastructure</li> <li>Security: WPA &amp; WPA2 Enterprise</li> <li>Authentificaiton: Protected EAP (PEAP)</li> <li>Anonymous identity: anonymous@kit.edu</li> <li>CA certificate: deutsche-telekom-root-ca-2.crt (<a href="http://www.scc.kit.edu/downloads/ism/dtag-root-ca-2.cer">source</a>)</li> <li>PEAP version: Automatic</li> <li>Inner authentification: MSCHAPv2</li> <li>Username: <ul> <li>for <code>wkit-802.1x</code>: uabcd (Your username. It begins with ‘u’ and has 5 letters)</li> <li>for <code>eduroam</code>: uabcd@student.kit.edu</li> </ul> </li> <li>Password: (Your password)</li> <li>IPv4 Settings: Automatic (DHCP)</li> <li>IPv6 Settings: Ignore</li> </ul> <h2 id="vpn">VPN</h2> <p>I use Juniper VPN.</p> <p>The following lines install some prerequesites, download Juniper from <a href="http://www.scc.kit.edu/dienste/7868.php">this page</a>, unpack it and execute the shell script.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install libc6-i386 lib32z1 lib32nss-mdns wget http://www.scc.kit.edu/scc/sw/juniper/7.4R8/linux_vpn_7.4R8.tar.gz tar -xzvf linux_vpn_7.4R8.tar.gz cd juniper_linux ./vpn-install.sh </pre></div> </div> </div> <p>After you have done this, you can use juniper with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>jnc -n kit </pre></div> </div> </div> <p>The <code>-n</code> flag disables GUI. It will show this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Server certificate verified and CN is vpn.kit.edu. Saving in /home/moose/.juniper_networks/network_connect/config/vpn.kit.edu.der. Password: Connecting to vpn.kit.edu : 443. Waiting for ncsvc for 3 seconds... done ncsvc is running, but tunnel is not established yet. Waiting for 3 seconds... done ncsvc is running, but tunnel is not established yet. Waiting for 3 seconds... done. ncsvc is running in background (PID: 11180): tunnel interface tun0, addr: 141.3.192.60 </pre></div> </div> </div> <p>You can stop it with <code>jnc stop</code>.</p> <h2 id="resources">Resources</h2> <ul> <li><a href="http://www.scc.kit.edu/dienste/kit-ca.php">Zertifizierung (KIT-CA)</a></li> <li><a href="http://www.scc.kit.edu/dienste/7868.php">Juniper VPN unter Linux</a></li> </ul> Sublime Text //martin-thoma.com/sublime-text/ Sat, 01 Mar 2014 17:01:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sublime-text <p>Sublime Text is the coolest editor I have ever used. It has a lot of features, is blazingly fast as I expect it from every editor and has a convenient configuration. It is available for Linux, Windows and Mac. You can use it for free without any restrictions as long as you want. But keep in mind that somebody had to develop this nice software.</p> <h2 id="installation">Installation</h2> <p>You can get a free version from <a href="http://www.sublimetext.com/">sublimetext.com</a> or you could install it on Linux Mint via</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install sublime-text </pre></div> </div> </div> <p>I’ve added a symlink to make it easier to call it from command line:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo ln -s /opt/sublime_text/sublime_text /usr/local/bin/sublime </pre></div> </div> </div> <p>The editor is usable right after the installation, but you might want to make some fine-tuning.</p> <h2 id="package-control">Package Control</h2> <p>The <a href="https://sublime.wbond.net/"><code>Package Control</code></a> plugin should definitely be installed. It makes installation of other packages so much easier. After you have installed it, you can press <kbd>Ctrl</kbd>+<kbd>Shift</kbd>+<kbd>P</kbd> to get this dialog:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-package-control-install.png"><img src="//martin-thoma.com/captions/sublime-package-control-install.png" alt="Sublime Tabs" width="500" height="186" class="" /></a><p class="wp-caption-text">Sublime Tabs</p></div> <h2 id="configuration">Configuration</h2> <p>Sublime Text offers plenty of configuration options. You can apply them to projects, users or system wide. Most of the time, I change my preferences for me via Preferences &gt; Settings - User:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-user-preferences.png"><img src="//martin-thoma.com/captions/sublime-user-preferences.png" alt="Preferences &gt; Settings - User" width="500" height="269" class="" /></a><p class="wp-caption-text">Preferences &gt; Settings - User</p></div> <p>Here is what I have changed:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>{ &quot;WrapPlus.break_on_hyphens&quot;: false, &quot;color_scheme&quot;: &quot;Packages/Colorsublime - Themes/textmate.tmTheme&quot;, &quot;detect_indentation&quot;: false, &quot;draw_white_space&quot;: &quot;all&quot;, &quot;fold_buttons&quot;: true, &quot;font_face&quot;: &quot;Ubuntu Mono&quot;, &quot;font_size&quot;: 15, &quot;highlight_line&quot;: true, &quot;rulers&quot;: [ 79, 120 ], &quot;scroll_speed&quot;: 0, &quot;search_threshold&quot;: 1000000, &quot;tab_size&quot;: 4, &quot;translate_tabs_to_spaces&quot;: true, &quot;use_tab_stops&quot;: false } </pre></div> </div> </div> <p>Note that you have to install the color scheme and the font (<a href="http://font.ubuntu.com/">source</a>) to use it.</p> <h2 id="command-palette">Command Palette</h2> <p>You can get to the command palette by <kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>P</kbd>. This opens such a dialog:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-command-palette.png"><img src="//martin-thoma.com/captions/sublime-command-palette.png" alt="Command Palette" width="500" height="281" class="" /></a><p class="wp-caption-text">automatical alignment</p></div> <p>This will do a fuzzy search through all elements in the menu. So you don’t need to use <kbd>Alt</kbd> + arrow keys no longer. I love it ☺</p> <h2 id="plugins">Plugins</h2> <h3 id="latextools">LaTeXTools</h3> <p>The <a href="https://github.com/SublimeText/LaTeXTools">LaTeXTools</a> package adds support for LaTeX. It adds shortcuts, a pull-down menu when you enter <code>\cref{</code> and much more.</p> <h3 id="brackethighlighter">BracketHighlighter</h3> <p><a href="https://github.com/facelessuser/BracketHighlighter">BracketHighlighter</a> adds brackets on the left side. It looks like this:</p> <div style="width: 338px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-braces.png"><img src="../images/2014/03/sublime-braces.png" alt="Highlight braces" width="" height="" class="" /></a><p class="wp-caption-text">Highlight braces</p></div> <h3 id="alignment">Alignment</h3> <p><a href="http://wbond.net/sublime_packages/alignment">Sublime Alignment</a> gives you the possibility to mark text, press <kbd>Ctrl</kbd>+<kbd>Alt</kbd>+<kbd>a</kbd> to align:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-align.gif"><img src="../images/2014/03/sublime-align.gif" alt="automatical alignment" width="" height="" class="" /></a><p class="wp-caption-text">automatical alignment</p></div> <h3 id="colorsublime">Colorsublime</h3> <p>Colorsublime is a plugin for theming Sublime Text&amp;nbps;3 within seconds. Take a look at <a href="http://colorsublime.com/">colorsublime.com</a> for some examples.</p> <h3 id="trailingspaces">TrailingSpaces</h3> <p>Tools for easy removing trailing spaces with <kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>T</kbd>. See <a href="https://github.com/SublimeText/TrailingSpaces">GitHub repository</a>.</p> <h3 id="wrap-plus">Wrap Plus</h3> <p>Tools for easy wrapping lines with <kbd>Alt</kbd> + <kbd>Q</kbd>. See <a href="https://github.com/ehuss/Sublime-Wrap-Plus">GitHub repository</a>.</p> <h3 id="python-flake8-lint">Python Flake8 Lint</h3> <p>Highlight potential problems with Python code. See <a href="https://github.com/dreadatour/Flake8Lint">GitHub repository</a>.</p> <h2 id="themes">Themes</h2> <p>First of all, make sure you have installed the <code>Colorsublime</code> package. After you have it, you can press <kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>P</kbd> and enter “Install Theme”. Then it contacts the server and provides you a list of many good themes. You can go through them with the arrow keys and they will instantly be applied!</p> <p>I really like the “Textmate” theme, but the “Chrome_DevTools” theme is also good.</p> <h2 id="custom-keybindings">Custom Keybindings</h2> <p>You can create custom keybindings via <em>Preferences Key Bindings (User)</em></p> <p>I have these:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[ { &quot;keys&quot;: [&quot;ctrl+shift+r&quot;], &quot;command&quot;: &quot;reindent&quot;, &quot;args&quot;: { &quot;single_line&quot;: false } }, { &quot;keys&quot;: [&quot;shift+tab&quot;], &quot;command&quot;: &quot;unindent&quot;, &quot;args&quot;: {&quot;single_line&quot;:true} }, { &quot;keys&quot;: [&quot;ctrl+7&quot;], &quot;command&quot;: &quot;toggle_comment&quot;, &quot;args&quot;: { &quot;block&quot;: false } }, { &quot;keys&quot;: [&quot;ctrl+shift+7&quot;], &quot;command&quot;: &quot;toggle_comment&quot;, &quot;args&quot;: { &quot;block&quot;: true } }, { &quot;keys&quot;: [&quot;ctrl+shift+t&quot;], &quot;command&quot;: &quot;delete_trailing_spaces&quot; } ] </pre></div> </div> </div> <h2 id="custom-snippets">Custom snippets</h2> <p>Snippets are a very cool feature of <abbr title="Sublime Text">ST</abbr>. They allow you to enter some text, press <kbd>Tab</kbd> and get whatever you wanted. So you could create a new <tt>.tex</tt> document, enter <tt>article</tt>, press <kbd>Tab</kbd> and get a template for a LaTeX document of the article document class.</p> <p>A tutorial how to create a snippet for the <tt>article</tt> document class was written Jonathan Page: <a href="http://economistry.com/2013/01/creating-snippets-in-sublime-text-2-for-latex/">Creating Snippets in Sublime Text 2 for LaTeX</a></p> <h2 id="buildin-keybindings">Buildin Keybindings</h2> <p><kbd>Ctrl</kbd> + <kbd>p</kbd>: Goto file</p> <p><kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>P</kbd>: Goto anything</p> <p><kbd>Ctrl</kbd> + <kbd>r</kbd>: Goto section</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-latextools-jump-ctrl-r.png"><img src="//martin-thoma.com/captions/sublime-latextools-jump-ctrl-r.png" alt="Ctrl+R in Sublime Text" width="500" height="326" class="" /></a><p class="wp-caption-text">Ctrl+R in Sublime Text (LaTeX)</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-jump-markdown-ctrl-r.png"><img src="//martin-thoma.com/captions/sublime-jump-markdown-ctrl-r.png" alt="Ctrl+R in Sublime Text" width="500" height="265" class="" /></a><p class="wp-caption-text">Ctrl+R in Sublime Text (Markdown)</p></div> <p><kbd>Ctrl</kbd> + <kbd>Shift</kbd> + <kbd>Up / Down</kbd>: Move the current line one line up / down</p> <p><kbd>Shift</kbd> + <kbd>F11</kbd>: Distraction free mode</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-text-distraction-free.png"><img src="//martin-thoma.com/captions/sublime-text-distraction-free.png" alt="Distraction free mode" width="500" height="282" class="" /></a><p class="wp-caption-text">Distraction free mode</p></div> <p><kbd>Ctrl</kbd> + <kbd>D</kbd>: Multi-Select</p> <h2 id="what-could-be-better">What could be better</h2> <h3 id="chrome-like-tabs">Chrome-like Tabs</h3> <p>Look at this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-text-tabs.png"><img src="//martin-thoma.com/captions/sublime-text-tabs.png" alt="Sublime Tabs" width="500" height="167" class="" /></a><p class="wp-caption-text">Sublime Tabs</p></div> <p>Now compare it to this:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/chrome-tabs.png"><img src="//martin-thoma.com/captions/chrome-tabs.png" alt="Chrome Tabs" width="500" height="100" class="" /></a><p class="wp-caption-text">Chrome Tabs</p></div> <p>Chrome tabs look much cleaner, don’t they? Many others seem to think that, too (<a href="http://sublimetext.userecho.com/topic/19361-move-tabs-to-the-title-bar-like-in-google-chrome/">source</a>).</p> <h3 id="line-wrapping">Line Wrapping</h3> <p>Sublime Text 3 does wrap points and commas to the next line:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/sublime-word-wrapping.png"><img src="//martin-thoma.com/captions/sublime-word-wrapping.png" alt="line wrapping" width="500" height="53" class="" /></a><p class="wp-caption-text">line wrapping</p></div> <p>This behaviour is bad and not liked by the community (<a href="http://www.sublimetext.com/forum/viewtopic.php?f=3&amp;t=5214">source</a>).</p> <h3 id="support-for-tooltips">Support for Tooltips</h3> <p>It would be absolutely great for many plugins like linters if they could make use of tooltips.</p> <blockquote> <p>Any news on tooltip and sidebar API? Are you planning to implement this (ever? :mrgreen: ) It’s something I very much want to get done, but at this stage I don’t know when that will be.</p> </blockquote> <p>Source: <a href="http://www.sublimetext.com/forum/viewtopic.php?f=2&amp;t=10780&amp;p=42383&amp;hilit=+tooltip#p42383">Sublime Text Forum: Sublime Text 3 Beta</a></p> <h2 id="more">More</h2> <ul> <li><a href="https://www.sublimetext.com/docs/3/">Documentation</a></li> <li><a href="http://colorsublime.com/">colorsublime.com</a>: Lots of themes</li> <li><a href="http://tmtheme-editor.herokuapp.com/#/theme/Chrome%20DevTools">tmtheme-editor.herokuapp.com</a>: Adjust your theme online</li> <li><a href="https://www.youtube.com/watch?v=5AV9zJH2n_Y&amp;index=2&amp;list=PLmJpVU-TdmVtTLooKvX3jcrOziPjlWrD4">Sublime Text 2 Video Tutorials</a>: A series of 32 video tutorials for Sublime Text 2. At least the first few are the same in ST 3.</li> </ul> GeoTopo Klausur //martin-thoma.com/geotopo/ Tue, 28 Jan 2014 17:39:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/geotopo <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Einführung in die Geometrie und Topologie&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn Prof. Dr. Herrlich im Wintersemester 2013/2014 gehört.</div> <p>Der Artikel wird bis zur Klausur laufend aktualisiert.</p> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <p>Ist im Skript:</p> <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/blob/master/documents/GeoTopo/GeoTopo.pdf?raw=true">PDF in A4</a> mit Links zum online anschauen</li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/blob/master/documents/GeoTopo/other-formats/GeoTopo-A5.pdf?raw=true">PDF in A5</a> zum ausdrucken und binden</li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/blob/master/documents/GeoTopo/definitions/definitionen.pdf?raw=true">Definitionen als PDF in A7</a> zum Karteikarten-Lernen</li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/GeoTopo">LaTeX-Quelldateien</a></li> </ul> <h2 id="material">Material</h2> <ul> <li><a href="https://studium.kit.edu/meineuniversitaet/Seiten/vorlesungsverzeichnis.aspx?page=event.asp&amp;gguid=0xe0d2509d5f1a744aaa9e74e22651d39c">Vorlesungsverzeichnis</a></li> <li><a href="http://www.math.kit.edu/iag3/lehre/einfgeotopo2013w/de">Vorlesungsseite</a></li> <li><a href="https://ilias.studium.kit.edu/goto_produktiv_fold_272864.html">Übungsblätter</a></li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <ul> <li>Wo sind die Übungsblätter: <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/uebung/#unterlagen">Link</a>&lt;/li&gt;</li> <li>Abgabeform: Über den Kasten im Allianzbau (bei der Mathe-Fachschaft)</li> <li>Abgabe: Montags</li> <li>Rücknahme: Im Tutorium</li> <li>Turnus: wöchentlich, erscheint am Montag</li> <li>Übungsschein verpflichtend: Es gibt keinen Übungsschein.</li> <li>Bonus durch Übungsschein: Es gibt keinen Klausurbonus.</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Samstag, den 22. Februar 2014 von 12:00 bis 14:00 Uhr<br /> <strong>Ort</strong>: Audimax (<a href="http://www.math.kit.edu/iag3/lehre/einfgeotopo2013w/event/klausur/">Quelle</a>)<br /> <strong>Punkte</strong>: 36<br /> <strong>Bestehensgrenze</strong>: 14 (?)<br /> <strong>Übungsschein</strong>: Gibt es nicht.<br /> <strong>Bonuspunkte</strong>: Gibt es nicht.<br /> <strong>Ergebnisse</strong>: sind ab heute Nachmittig im Studierendenportal (Stand: 28.02.2014)<br /> <strong>Einsicht</strong>: Montag, 17. März um 15.00 Uhr im Raum 1C-03 (Stand: 28.02.2014, <a href="https://ilias.studium.kit.edu/ilias.php?ref_id=271974&amp;cmd=frameset&amp;cmdClass=ilrepositorygui&amp;cmdNode=ed&amp;baseClass=ilRepositoryGUI">Quelle</a>)<br /> <strong>Erlaubte Hilfsmittel</strong>: Keine.<br /> <strong>Mitbringen</strong>: Studentenausweis und Stift.</p> <h2 id="ergebnisse">Ergebnisse</h2> <p>Im <a href="https://studium.kit.edu/">Studierendenportal</a> (Stand: 28.02.2014).</p> Highend Notebooks //martin-thoma.com/highend-notebooks/ Tue, 28 Jan 2014 16:00:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/highend-notebooks <p>My <a href="../review-des-acer-travelmate-5744z/">Acer Travelmate 5744Z</a> seems to get broken in soon, so I’m currently looking for a new notebook. As I use my notebook quite often and as this is the third notebook within three years that is not usable any longer (the screen of the first is defect and the graphic card / WLAN of the second does not work propperly with the new Linux kernel), I’m would like to have a high end notebook this time. I hope that I not have to think about notebooks for at least 5 years after that.</p> <h2 id="requirements">Requirements</h2> <p>I work quite a lot with the computer, so the keyboard and the display have to be good. What does good mean? Well, the display has to be <strong>at least 15”</strong> and as I don’t want to see my pixels any longer it has to have a <strong>higher resolution than 1366×768</strong>. But it has to be <strong>smaller than 30cm × 38cm</strong> to fit into my knapsack. A reason why I do not always have my current notebook with me is that it is too heavy with about 2.5kg and does only run for about 3.5h. The new one should be <strong>lighter than 2.5kg</strong> and <strong>run at least 4h</strong>.</p> <p><strong>Ubuntu</strong> has to be supported completely, especially WLAN, sound and Bluetooth. Speaking of Bluetooth, I want <strong>Bluetooth 4.0</strong>, because it introduced a low energy protocol that might be usefull for notebooks. As I live in a city and as I access the internet via my neighbors WLAN (thank you!), I need a good connection: <strong>Dual band and 802.11a/b/g/n</strong> need to be supported by the notebook. (Dual band is sometimes also called 2x2).</p> <p>I use it mainly for writing blog articles, LaTeX stuff and some Python programming and watching movies. I download movies via Online TV Recorder which sums up quite soon. Transfering this to my external HDD always takes a lot of time. The new notebook should support <strong>USB 3.0</strong> to speed this up. As I don’t have to store anything large, <strong>80 GB SSD</strong> is enough. It should be a SSD, because they consume less power, are more durable and are more silent.</p> <p>I need at least <strong>4GB RAM</strong> because … well, did you ever try to use Eclipse for Java+JBoss programming with less than 4GB? I don’t want to have that again.</p> <p>It would be nice if I could use the notebook outside in the summer which means it has to have a <strong>bright matte display</strong>.</p> <p>I want a silent notebook, because I’m very sensitive to noise. My current notebook has <strong>less than 30 dB in normal mode</strong> (no heavy load). That should set the mark.</p> <p>Another keyboard-thing: <kbd>Ctrl</kbd> has to be at the lower left (→ no thinkpads).</p> <p>A SD-Card Reader would be nice, but it is not required. Just like a RJ-45 for network cables and a DVD drive you can get it via USB.</p> <p>I robust case is also important. I had troubles working in the train, because the screen was whipping as hell. But this is not a hard requirement for me as I don’t work in trains that often.</p> <h2 id="current-favorites">Current Favorites</h2> <p>I’ve looked at a lot of notebooks and I did mainly focus on the technical specification and not at the price (I guess I might work about 10h every day in front of this machine. A good, working notebook is very important to me). However, when I see some notebooks that are ok according to the specs from above, I will take the cheaper one.</p> <p>By the way, while searching for notebooks I discovered that much of the data on Amazon is wrong. See for example the dimensions of the HP EliteBook 8570p-B6Q03EA-ABD (51.6 x 34.2 x 7.8 cm according to Amazon).</p> <table> <thead> <tr> <th> </th> <th>Asus Zenbook</th> <th>Samsung Notebook Serie 9</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>UX51VZ-DB114H</td> <td>900X4D K01</td> </tr> <tr> <td>Price</td> <td>1380 Euro</td> <td>995 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>380 × 254 × 20</td> <td>356.9 × 237 × 14.9 mm</td> </tr> <tr> <td>Weight</td> <td>2.2 kg</td> <td>1.58 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i7 3632QM</td> <td><a href="http://ark.intel.com/products/72055">Intel Core i5-3337U</a></td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> <td>15”</td> </tr> <tr> <td>Display Resolution</td> <td>2880×1620</td> <td>1600×900</td> </tr> <tr> <td>Display more</td> <td> </td> <td>LED-Display, 400 Nit</td> </tr> <tr> <td>Matte display</td> <td>✘</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>8 GB DDR3, 1600 MHz</td> <td>2× 4 GB DDR3 SDRAM1.600 MHz</td> </tr> <tr> <td>Disk</td> <td>256 SSD</td> <td>128 GB SSD</td> </tr> <tr> <td>Network</td> <td>?</td> <td>RJ45 with adapter and 1.000 Mbit/s</td> </tr> <tr> <td>Wireless</td> <td>802.11a/g/n, WiDi</td> <td>802.11a/b/g/n (2×2), WiDi</td> </tr> <tr> <td>WLAN-Chip</td> <td>?</td> <td>Intel Wireless-N 7260</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>4750 mAh</td> <td>8200 mAh, up to 10h</td> </tr> <tr> <td>USB</td> <td>3× USB 3.0</td> <td>2× USB 3.0, 1× USB 2.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> <td>partially ([^1],[^2], [^3])</td> </tr> <tr> <td>Keyboard</td> <td>?</td> <td>Chiclet-keyboard without numblock</td> </tr> <tr> <td>Noise</td> <td>?</td> <td>29.5 dB in normal mode, 40 dB max</td> </tr> </tbody> </table> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/01/samsung-serie-9-keyboard-layout.png" class="image"><img src="//martin-thoma.com/captions/samsung-serie-9-keyboard-layout.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Samsung Series 9</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2014/01/macbook-pro-retina-keyboard-layout.jpg" class="image"><img src="//martin-thoma.com/captions/macbook-pro-retina-keyboard-layout.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Macbook Pro</div></div></li></ul> <p>The WLAN chipset of the Samsung Serie 9 seems to cause trouble with Linux, but it also seems to be solved by a firmware update.[^5] But one hint seems to be important:</p> <blockquote> <p>Before you install Linux on a Samsung Serie 9, make sure you update the firmware, because that’s only possible with Windows.</p> </blockquote> <p>Asus Zenbook seems also to work almost out of the box.[^6] I’ve just learned that you can use</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo dmidecode -s system-product-name </pre></div> </div> </div> <p>to determine your exact laptop product name.</p> <p>In the following, I will give you an overview of the notebooks I took a look at. I think all of them are very good.</p> <p>In many cases I will need some more equipment:</p> <ul> <li>MicroHDMI 2 VGA adapter: Samsung AA-AH2NMHB/E for 29.90 Euro</li> <li>USB Ethernet adapter: “Cable Matters - SuperSpeed USB 3.0” for 16 Euro</li> <li>External DVD burner: Samsung SE-208DB for 30 Euro works with DVD±R Dual layer disks and DVD±RW disks. Is there anything more important to look at?</li> </ul> <h2 id="acer">Acer</h2> <table> <thead> <tr> <th> </th> <th>Acer Aspire</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>V5-573G-54208G50aii</td> </tr> <tr> <td>Price</td> <td>649 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>382 × 256 × 18</td> </tr> <tr> <td>Weight</td> <td>2.04 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i5-4200U</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1920 × 1080</td> </tr> <tr> <td>Matte display</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>8 GB DDR3, 1600 MHz</td> </tr> <tr> <td>Disk</td> <td>1000 GB HDD</td> </tr> <tr> <td>Network</td> <td>10/100/1000MBit</td> </tr> <tr> <td>Wireless</td> <td> </td> </tr> <tr> <td>WLAN-Chip</td> <td>Atheros AR5BWB222</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>3560 mAh</td> </tr> <tr> <td>USB</td> <td>1× USB 3.0, 2× USB 2.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>✔</td> </tr> <tr> <td>Keyboard</td> <td>Chiclet-Keyboard</td> </tr> <tr> <td>Noise</td> <td>33.3 dB</td> </tr> </tbody> </table> <h2 id="apple">Apple</h2> <table> <thead> <tr> <th> </th> <th>Macbook Pro</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>Retina 15”</td> </tr> <tr> <td>Price</td> <td>1999 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>358.9 × 247.1 × 18 mm</td> </tr> <tr> <td>Weight</td> <td>2.02 kg</td> </tr> <tr> <td>CPU</td> <td><a href="http://ark.intel.com/products/53474">Intel Core i7 2760QM</a></td> </tr> <tr> <td>Display Size</td> <td>15.4”</td> </tr> <tr> <td>Display Resolution</td> <td>2880×1800</td> </tr> <tr> <td>Display more</td> <td> </td> </tr> <tr> <td>Matte display</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>8 GB 1600 MHz DDR3L</td> </tr> <tr> <td>Disk</td> <td>256 SSD</td> </tr> <tr> <td>Network</td> <td>no RJ45</td> </tr> <tr> <td>Wireless</td> <td>802.11a/b/g/n</td> </tr> <tr> <td>WLAN-Chip</td> <td>?</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>up to 7h</td> </tr> <tr> <td>USB</td> <td>2× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>Chiclet-Keyboard</td> </tr> <tr> <td>Noise</td> <td>29.4 dB in normal mode, 47.4 dB max</td> </tr> </tbody> </table> <p>Although the hardware looks very nice, it is still comparable with both of my favorites.</p> <h2 id="asus">Asus</h2> <h3 id="asus-zenbooks">Asus Zenbooks</h3> <table> <thead> <tr> <th> </th> <th>Asus Zenbook</th> <th>Asus Zenbook</th> <th>Asus Zenbook</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>UX51VZ-CN035H</td> <td>UX51VZ-DB114H</td> <td>U500VZ</td> </tr> <tr> <td>Price</td> <td>1390 Euro</td> <td>1380 Euro</td> <td>1350 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>380 × 254 × 20</td> <td>380 × 254 × 20</td> <td>380 × 254 × 20 mm</td> </tr> <tr> <td>Weight</td> <td>2.2 kg</td> <td>2.2 kg</td> <td>2.2 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i7-3612QM</td> <td>Intel Core i7 3632QM</td> <td>Intel Core i7-3612QM</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> <td>15.6”</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1920×1080</td> <td>2880×1620</td> <td>1920×1080</td> </tr> <tr> <td>Matte display</td> <td>✔</td> <td>✘</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>8 GB DDR3, 1600 MHz</td> <td>8 GB DDR3, 1600 MHz</td> <td>4 GB</td> </tr> <tr> <td>Disk</td> <td>256 SSD</td> <td>256 SSD</td> <td>512 GB SSD</td> </tr> <tr> <td>Network</td> <td>10/100/1000, RJ45</td> <td>?</td> <td>?</td> </tr> <tr> <td>Wireless</td> <td>802.11a/g/n, 2×2 WiDi</td> <td>802.11a/g/n, WiDi</td> <td>802.11a/b/g/n, 2×2</td> </tr> <tr> <td>WLAN-Chip</td> <td>?</td> <td>?</td> <td>?</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> <td>4.0</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>?</td> <td>4750 mAh</td> <td>4750 mAh</td> </tr> <tr> <td>USB</td> <td>3× USB 3.0</td> <td>3× USB 3.0</td> <td>2× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> <td>✔</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> <td>?</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>?</td> <td>?</td> <td>Chiclet-Keyboard with Numblock</td> </tr> <tr> <td>Noise</td> <td>?</td> <td>?</td> <td>34 dB in normal mode, 42 dB max</td> </tr> </tbody> </table> <h3 id="asus-pu500ca-xo002x-and-asus-n550jv-cn201h">Asus PU500CA-XO002X and Asus N550JV-CN201H</h3> <table> <thead> <tr> <th> </th> <th>Asus</th> <th>Asus</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>PU500CA-XO002X</td> <td>N550JV-CN201H</td> </tr> <tr> <td>Price</td> <td>998 Euro</td> <td>1099</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>383 × 257 × 22.5 mm</td> <td>383 × 255 × 27</td> </tr> <tr> <td>Weight</td> <td>1.96 kg</td> <td>2.7 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i5-3317U</td> <td>Intel Core i7-4700HQ</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1366 × 768</td> <td>1920 × 1080</td> </tr> <tr> <td>Matte display</td> <td>✔</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>4 GB</td> <td>8GB DDR3</td> </tr> <tr> <td>Disk</td> <td>524 GB</td> <td>1000 GB HDD</td> </tr> <tr> <td>Network</td> <td>?</td> <td>?</td> </tr> <tr> <td>Wireless</td> <td>802.11 a/b/g/n, WiDi</td> <td>802.11 b/g/n</td> </tr> <tr> <td>WLAN-Chip</td> <td> </td> <td>Atheros (AR9485)</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>4000 mAh, up to 7h</td> <td>4000 mAh</td> </tr> <tr> <td>USB</td> <td>1× USB 3.0</td> <td>2× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>Chiclet-Keyboard with Numblock</td> <td>Chiclet-Keyboard with Numblock</td> </tr> <tr> <td>Noise</td> <td>30.7 dB in normal mode, 38.4 dB max</td> <td>32.9 dB in normal mode, 38 dB max</td> </tr> </tbody> </table> <h2 id="dell">Dell</h2> <table> <thead> <tr> <th> </th> <th><a href="http://www.notebookcheck.com/Test-Dell-XPS-15-2015-Notebook.137681.0.html">XPS 15</a></th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>9530-1906</td> </tr> <tr> <td>Price</td> <td>1711 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>372 × 254 × 18</td> </tr> <tr> <td>Weight</td> <td>2.02 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i7-4702HQ</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>3200x1800</td> </tr> <tr> <td>Matte display</td> <td>✘</td> </tr> <tr> <td>RAM</td> <td>8 GB DDR3L, 1600 MHz</td> </tr> <tr> <td>Disk</td> <td>512 GB SSD</td> </tr> <tr> <td>Network</td> <td>(no RJ45)</td> </tr> <tr> <td>Wireless</td> <td>802.11 ac, 2x2</td> </tr> <tr> <td>WLAN-Chip</td> <td>Intel AC 7260</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>?</td> </tr> <tr> <td>USB</td> <td>3× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>Chiclet-Keyboard</td> </tr> <tr> <td>Noise</td> <td>29.8 dB, 42.1 dB max</td> </tr> </tbody> </table> <p>There seem to be other versions of the XPS 15:</p> <ul> <li>XPS 15 (L501X)</li> <li>XPS 15 (L502X)</li> <li>XPS 15z</li> </ul> <p>However, I was not able to find any specification of those.</p> <h2 id="fujitsu">Fujitsu</h2> <table> <thead> <tr> <th> </th> <th>Fujitsu Lifebook</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>E753</td> </tr> <tr> <td>Price</td> <td>1759 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>374 × 374 × 20</td> </tr> <tr> <td>Weight</td> <td>1.99 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i7-3632QM</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1920×1080</td> </tr> <tr> <td>Matte display</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>8 GB DDR3</td> </tr> <tr> <td>Disk</td> <td>256 GB SSD</td> </tr> <tr> <td>Network</td> <td>10/100/1000MBit</td> </tr> <tr> <td>Wireless</td> <td>802.11 a/b/g/n</td> </tr> <tr> <td>WLAN-Chip</td> <td>Centrino Advanced-N 6235</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>6700 mAh</td> </tr> <tr> <td>USB</td> <td>3× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>Chiclet-Keyboard</td> </tr> <tr> <td>Noise</td> <td>33.3 dB</td> </tr> </tbody> </table> <h2 id="hp">HP</h2> <table> <thead> <tr> <th> </th> <th>HP Envy 15</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>J011SG</td> </tr> <tr> <td>Price</td> <td>811 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>380 × 251 × 28</td> </tr> <tr> <td>Weight</td> <td>2.19 kg</td> </tr> <tr> <td>CPU</td> <td>Intel Core i5-4200M</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1920×1080</td> </tr> <tr> <td>Matte display</td> <td>✘</td> </tr> <tr> <td>RAM</td> <td>12 GB DDR3L, 1600 MHz</td> </tr> <tr> <td>Disk</td> <td>1000 GB</td> </tr> <tr> <td>Network</td> <td>10/100/1000 RJ-45</td> </tr> <tr> <td>Wireless</td> <td>802.11b/g/n</td> </tr> <tr> <td>WLAN-Chip</td> <td>Intel AC 7260</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>2200 mAh</td> </tr> <tr> <td>USB</td> <td>4× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>with numblock</td> </tr> <tr> <td>Noise</td> <td>?</td> </tr> </tbody> </table> <h2 id="samsung">Samsung</h2> <h3 id="serie-9">Serie 9</h3> <p>The next few lines show the difference of the <code>900X4C A0A</code> to…</p> <ul> <li><code>NP900X4C-A01</code>: Intel Core i5-3317U, 128GB SSD, no Dualband</li> <li><code>900X3C A03</code>: 3610 mAh, 1399 Euro</li> <li><code>900X4B-A01</code>: Intel Core i7 2637M, 1999 Euro</li> <li><code>900X4C-A04</code>: Intel Core i5 3317U, 1999 Euro</li> <li><code>900X4C-A05</code>: Intel Core i5 3317U, 128GB SSD, no Dualband, ca 1200 Euro</li> <li><code>900X4C A06</code>: 256 GB SSD, 15.6” Display, 1629 Euro</li> <li><code>900X4C A09</code>: Costs 1999 Euro (any other difference?)</li> <li><code>900X4D A03</code> has also 15” Display, but only 4GB RAM and a <a href="http://ark.intel.com/products/65707">Intel Core i5-3317U</a> and a 128 GB SSD. But it costs only 799 Euro.</li> <li><code>900X4D K01</code>: Intel Core i5-3337U, 128 GB SSD, 8400 mAh, Dual Band, 997 Euro</li> </ul> <h3 id="samsung-ativ-book-9-2014-edition">Samsung ATIV Book 9 2014 Edition</h3> <table> <thead> <tr> <th> </th> <th>Samsung ATIV Book 9 2014 Edition</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>NP930X5J-K01DE</td> </tr> <tr> <td>Price</td> <td>1599 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>? × ? × 14.9 mm</td> </tr> <tr> <td>Weight</td> <td>1.78 kg</td> </tr> <tr> <td>CPU</td> <td><a href="http://ark.intel.com/products/75460">Intel Core i7-4500U</a></td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1920×1080</td> </tr> <tr> <td>Display more</td> <td>Touch-Display</td> </tr> <tr> <td>Matte display</td> <td>✘</td> </tr> <tr> <td>RAM</td> <td>8 GB ? MHz</td> </tr> <tr> <td>Disk</td> <td>256GB SSD</td> </tr> <tr> <td>Network</td> <td>RJ45 with adapter and 1.000 Mbit/s</td> </tr> <tr> <td>Wireless</td> <td>802.11 ac (2x2) (<a href="http://de.samsung.com/webdownloads/pressedownloads/Presseinformation_Samsung_ATIV_Book_9_Edition_2014_1.pdf">source</a>)</td> </tr> <tr> <td>WLAN-Chip</td> <td>Intel Wireless-AC 7260, 802.11 ac</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>?, 14h</td> </tr> <tr> <td>USB</td> <td>2× USB 3.0, 1 × USB 2.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>?</td> </tr> <tr> <td>Keyboard</td> <td>Chiclet-keyboard</td> </tr> <tr> <td>Noise</td> <td>?</td> </tr> </tbody> </table> <ul> <li>Good audio qualit: 24-bit, 192kHz audio, 2x 2W</li> <li>HDMI out, mini VGA, an SD card reader</li> <li>720p webcam</li> </ul> <p>Release date should be 28.03.2014 (<a href="http://www.arlt.com/Notebook/Ultrabooks/Samsung/Samsung-ATIV-Book-9-NP930X5J-K01DE-2014-Edition.html">source</a>).</p> <h4 id="sources">Sources</h4> <ul> <li><a href="http://www.techradar.com/reviews/pc-mac/laptops-portable-pcs/laptops-and-netbooks/samsung-ativ-book-9-2014-edition-1212115/review">techradar.com</a></li> <li><a href="http://www.notebookcheck.com/Samsung-praesentiert-Notebook-Ativ-Book-9-2014-Edition.108498.0.html">notebookcheck.de</a></li> </ul> <h2 id="tuxedo">Tuxedo</h2> <table> <thead> <tr> <th> </th> <th>Tuxedo Book</th> </tr> </thead> <tbody> <tr> <td>Model</td> <td>BC1503</td> </tr> <tr> <td>Price</td> <td>763 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>374 × 252 × 31 mm</td> </tr> <tr> <td>Weight</td> <td>2.4 kg</td> </tr> <tr> <td>CPU</td> <td><a href="http://ark.intel.com/products/76348">Intel Core i5 4200M</a></td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>1920×1080</td> </tr> <tr> <td>Display more</td> <td>IPS-Display</td> </tr> <tr> <td>Matte display</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>1×8 GB 1600 MHz</td> </tr> <tr> <td>Disk</td> <td>120 SSD (Samsung EVO / SATA III)</td> </tr> <tr> <td>Network</td> <td>has RJ45 built-in, 10/100/1000</td> </tr> <tr> <td>Wireless</td> <td>802.11 ac/a/b/g/n</td> </tr> <tr> <td>WLAN-Chip</td> <td>Intel Dual AC7260</td> </tr> <tr> <td>Bluetooth</td> <td>4.0</td> </tr> <tr> <td>Akku</td> <td>62,16 Wh, 2.5h[^4]</td> </tr> <tr> <td>USB</td> <td>2× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>✔</td> </tr> <tr> <td>Linux-Support</td> <td>shipped with Linux Mint ☺</td> </tr> <tr> <td>Keyboard</td> <td>?</td> </tr> <tr> <td>Noise</td> <td>Laut[^4]</td> </tr> </tbody> </table> <p>See also: <a href="https://www.tuxedocomputers.com/Linux-Hardware/Linux-Notebooks/15-6-Zoll/TUXEDO-Book-BU1505-15-6-matt-Full-HD-IPS-bis-Intel-Core-i7-Energiespar-CPU-zwei-HDD-SSD-bis-16GB-RAM-bis-10h-Akku-bel-Tastatur-Slim-Book-LTE-opt.geek">tuxedocomputers.com</a>, <a href="http://www.linux-onlineshop.de/Linux-Hardware/Linux-Notebooks/15-6-Zoll/TUXEDO-Book-BU1505-15-6-matt-Full-HD-IPS-bis-Intel-Core-i7-Energiespar-CPU-zwei-HDD-SSD-bis-16GB-RAM-bis-10h-Akku-bel-Tastatur-Slim-Book-LTE-opt.geek">linux-onlineshop.de</a></p> <ul> <li>TUXEDO Book BU1505 (with Skylake, up to 16GB RAM, ca. 1240 Euro)</li> </ul> <h2 id="librem-15">Librem 15</h2> <table> <thead> <tr> <th> </th> <th><a href="https://puri.sm/librem-15/">Librem 15</a></th> </tr> </thead> <tbody> <tr> <td>Model</td> <td> </td> </tr> <tr> <td>Price</td> <td>2185 Euro</td> </tr> <tr> <td>Dimensions (B × D × H)</td> <td>375 × 244 × 22 mm</td> </tr> <tr> <td>Weight</td> <td>2.0 kg</td> </tr> <tr> <td>CPU</td> <td><a href="http://ark.intel.com/products/84993/Intel-Core-i7-5557U-Processor-4M-Cache-up-to-3_40-GHz">Intel i7-5557U</a> (Broadwell-U architecture)</td> </tr> <tr> <td>Display Size</td> <td>15.6”</td> </tr> <tr> <td>Display Resolution</td> <td>3840×2160</td> </tr> <tr> <td>Display more</td> <td>IPS-Display</td> </tr> <tr> <td>Matte display</td> <td>✔</td> </tr> <tr> <td>RAM</td> <td>1×8 GB 1600 MHz</td> </tr> <tr> <td>Disk</td> <td>250 GB SSD</td> </tr> <tr> <td>Network</td> <td>✘, 10/100/1000</td> </tr> <tr> <td>Wireless</td> <td>802.11 n</td> </tr> <tr> <td>WLAN-Chip</td> <td>?</td> </tr> <tr> <td>Bluetooth</td> <td>✔, ?</td> </tr> <tr> <td>Akku</td> <td>65W, 48 Wh, Up to 6 hours usage</td> </tr> <tr> <td>USB</td> <td>1× USB 3.1, 2× USB 3.0</td> </tr> <tr> <td>SD Card Reader</td> <td>SDXC</td> </tr> <tr> <td>Linux-Support</td> <td>✔</td> </tr> <tr> <td>Keyboard</td> <td>?</td> </tr> <tr> <td>Noise</td> <td>?</td> </tr> </tbody> </table> <h4 id="other">Other</h4> <p>On a first glance, the Samsung ATIV Book 8 NP880Z5E-X01 looked quite promising. But it doesn’t have an SSD, it weights 2.54 kg, but has no optical drive.</p> <ul> <li> <p>Samsung ATIV 870Z5E-X03DE</p> </li> <li>ATIV Book 8 870Z5E X04</li> <li>ATIV Book 8 880Z5E X01</li> <li>ATIV Book 9 900X4D K01 (<a href="http://www.notebookinfo.de/produkte/samsung-ativ-book-9-900x4d-k01/np900x4d-k01de/00016092/#Datenblatt">notebookinfo.de</a>)</li> </ul> <h2 id="notebooks-that-did-not-meet-the-criteria">Notebooks that did not meet the criteria</h2> <p>Display is too small:</p> <ul> <li>Chromebook Pixel has only 12.85”</li> <li>XPS 13 has only 13.3”</li> <li>Asus Zenbook has only 13.3”</li> <li>Lenovo IdeaPad U300s have only 13.3”</li> <li>All Samsung Series 9 X3A seem to have 13.3” displays</li> <li>Samsung Series 9 900X3D-A02: 13.3”</li> <li>Samsung Series 9 900X3C-A01: 13.3”</li> <li>Samsung Series 9 900X3C A07: 13.3”</li> </ul> <p>Too low resolution:</p> <ul> <li>Acer TravelMate 6594eG-464G50Mikk</li> <li>Asuspro PU500</li> <li>All Acer Aspire TimelineU M5</li> </ul> <p>To heavy:</p> <ul> <li>Lenovo IdeaPad Y510p: 2.89 kg</li> <li>HP EliteBook 8570p-B6Q03EA-ABD: 2.91 kg</li> <li>Sony Vaio VPC-F21Z1E/BI: 3.17 kg</li> </ul> <p>Availability: seems not to be available on Amazon</p> <ul> <li>Samsung Serie 9 NP900X4C-A02</li> <li>Sony Vaio SV-E1511V1EW</li> <li>Sony Vaio VGN-TX2</li> <li>HP Envy 6-1000sg</li> </ul> <p>Other:</p> <ul> <li>Acer Aspire M3-581TG: Too loud, only 667MHz RAM</li> </ul> <h2 id="dear-notebook-producers">Dear Notebook-Producers</h2> <p>After searching so much for notebooks, I have some hints for you what you could do better:</p> <ul> <li>Add a single specification page for each notebook. This page should include at least: <ul> <li>Weight in kg and dimensions in mm</li> <li>Battery life in mAh</li> <li>Display (size, glare or matte display, supported resolutions)</li> <li>Exact CPU name (not only Intel i5 - if it varies, list all possible CPUs)</li> <li>Disk (size, SSD or not)</li> <li>Wireless support (IEEE 802.11 supported standards? Dual band? Bluetooth? Bluetooth version?)</li> <li>Keyboard: Does it have a numblock? Backlit?</li> <li>Does it have a DVD-Player / Burner? Blue-Ray?</li> <li>Webcam (resolution)</li> <li>Microphone</li> <li>Sensors (GPS)</li> <li>Image of the notebook</li> </ul> </li> <li>A good specification page would include: <ul> <li>Noise in dB</li> <li>Information about Linux support (especially Debian)</li> </ul> </li> <li>Explain your version names!</li> <li>Provide a possibility to compare your products like Intel does with <a href="http://ark.intel.com/">ark.intel.com</a> for its processors</li> <li>Provide a possibility to filter your products by technical specification.</li> <li>Add an image of your product to Wikipedia Commons</li> </ul> <h2 id="references">References</h2> <p>[^1] <a href="http://blog.jospoortvliet.com/2012/09/linux-and-samsung-series-9-np900x3c.html">Linux and the Samsung Series 9 NP900X3C</a>: A review for the NP900X3C and openSUSE on 24th or September, 2012. [^2] <a href="https://help.ubuntu.com/community/SamsungSeries9">Samsung Series 9 - Ubuntu Community Page</a> [^3] <a href="http://www.sump.org/blog/213">Linux auf Samsung Series 9 2012</a> [^4] <a href="http://www.pcwelt.de/produkte/Tuxedo-Book_DC1502-Standard-Notebook-Test-8115776.html">Tuxedo Book DC1502 im Test</a> [^5] <a href="http://askubuntu.com/questions/322511/no-wireless-with-intel-centrino-advanced-n-7260">No wireless with Intel Centrino Advanced-N 7260</a> [^6] <a href="https://help.ubuntu.com/community/AsusZenbook">AsusZenbook - Ubuntu Community Page</a></p> Install and configure computer //martin-thoma.com/install-and-configure-computer/ Sat, 25 Jan 2014 10:14:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/install-and-configure-computer <p>When I reinstall my computer, I usually do these following steps:</p> <ol> <li>Copy all data to an external HDD</li> <li>Write down all WLAN configurations (eventually with screenshots; NOT ONLY PASSWORDS!)</li> <li>Write down all programs that I use.</li> <li>Export configuration of those programs.</li> <li>Wait a week or a month and see if someting is missing in the lists from above.</li> <li>Drop the old system and install a new one</li> </ol> <h2 id="software-i-usually-install">Software I usually install</h2> <p>If possible, I will give the debian package names in the following list:</p> <ul> <li><a href="../how-to-install-the-latest-latex-version/">LaTeX</a> and scientific writing <ul> <li><a href="//martin-thoma.com/reference-management-with-jabref/"><code>jabref</code></a>: A reference manager</li> <li><code>gnuplot</code></li> <li><code>pdf2svg</code></li> <li><code>aspell</code> and <code>aspell-de</code></li> </ul> </li> <li><a href="https://www.google.com/intl/de/chrome/browser/">Google Chrome</a></li> <li>Multimedia <ul> <li><a href="http://www.videolan.org/vlc/"><code>vlc</code></a>: A very good DVD player</li> <li><a href="http://wiki.ubuntuusers.de/OnlineTvRecorder">OnlineTvRecorder</a> and especially <a href="http://wiki.ubuntuusers.de/OTR-Verwaltung">OTR-Verwaltung</a> <ul> <li><code>avidemux wine mplayer</code></li> </ul> </li> <li><code>sudo add-apt-repository ppa:clipgrab-team &amp;&amp; sudo apt-get update &amp;&amp; sudo apt-get install clipgrab</code></li> </ul> </li> <li>Graphics <ul> <li><a href="http://www.gimp.org/"><code>gimp</code></a></li> <li><a href="http://www.inkscape.org/"><code>inkscape</code></a></li> <li><code>dia</code></li> <li><a href="http://www.imagemagick.org/script/index.php"><code>imagemagick</code></a></li> <li><code>pdf2svg librsvg2-bin</code></li> </ul> </li> <li>Programming <ul> <li><code>vim</code></li> <li><code>python python3 python-numpy python-setuptools python-mysqldb</code></li> <li><code>ruby ruby-sqlite3 ruby-mysql</code></li> <li><code>gcc g++ cmake build-essential gdb</code></li> <li>OpenGL: <code>xorg-dev libglu1-mesa-dev freeglut3 freeglut3-dev libglew1.5 libglew1.5-dev libglu1-mesa libglu1-mesa-dev libgl1-mesa-glx libgl1-mesa-dev</code></li> <li><code>apache2 php5 php5-mysql</code></li> <li><code>zsh</code> and <a href="../working-terminal/">Oh-my-zsh</a></li> <li><code>eclipse</code></li> <li><code>sqlitebrowser</code></li> <li><code>tcl</code></li> <li><code>phpmyadmin selfhtml</code></li> <li><code>meld diffpdf</code></li> <li><a href="https://wiki.ubuntuusers.de/virtualbox"><code>virtualbox</code></a></li> </ul> </li> <li>Themes <ul> <li>Balazan-Theme from <a href="http://www.bisigi-project.org/?page_id=8&amp;lang=en">bisigi-project</a> (simply download it.)</li> </ul> </li> <li>Other <ul> <li><a href="//martin-thoma.com/sublime-text/"><code>sublime_text</code></a></li> <li><code>libreoffice</code></li> <li><code>curl</code></li> </ul> </li> <li>DRM-caused (I want to watch DVDs!) <ul> <li><code>ubuntu-restricted-extras libdvd-pkg libdvdread4 libdvdnav4</code>, then run <code>sudo dpkg-reconfigure libdvd-pkg</code></li> <li><code>totem banshee mplayer rythmbox</code></li> </ul> </li> </ul> <h2 id="configure">Configure</h2> <h3 id="set-standards">Set standards</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>update-alternatives --config editor update-alternatives --config x-www-browser </pre></div> </div> </div> <h3 id="mate">MATE</h3> <p>See <a href="https://github.com/mate-desktop/caja/issues/262">issues/262</a>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>mv ~/.config/gtk-3.0/bookmarks ~/.config/gtk-3.0/bookmarks-backup ln -s ~/.gtk-bookmarks ~/.config/gtk-3.0/bookmarks </pre></div> </div> </div> <h3 id="gui">GUI</h3> <p>I like the old menu bar quite a lot. It opens instantly and is customizable:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/mate-old-menu.png"><img src="//martin-thoma.com/captions/mate-old-menu.png" alt="Old menu bar" width="500" height="317" class="" /></a><p class="wp-caption-text">Old menu bar</p></div> <p>You can get it back in MATE by doing a right-click on the menu. Then click on “add to panel”:</p> <div style="width: 297px" class="wp-caption aligncenter"><a href="../images/2014/03/mate-add-to-panel.png"><img src="../images/2014/03/mate-add-to-panel.png" alt="Add to panel" width="" height="" class="" /></a><p class="wp-caption-text">Add to panel</p></div> <p>After that, the following dialog will pop up. Choose “Menu Bar”</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2014/03/mate-add-menu-bar.png"><img src="//martin-thoma.com/captions/mate-add-menu-bar.png" alt="Add menu bar" width="500" height="458" class="" /></a><p class="wp-caption-text">Add menu bar</p></div> <h3 id="drm-stuff">DRM-Stuff</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo /usr/share/doc/libdvdread4/install-css.sh sudo regionset #use that with caution </pre></div> </div> </div> <h3 id="dotfiles">dotfiles</h3> <p>See <a href="https://github.com/MartinThoma/dotfiles">github.com/MartinThoma/dotfiles</a>.</p> <h2 id="data">Data</h2> <p>Download / copy all data back from GitHub / external HDDs to my internal HDD.</p> SLURM //martin-thoma.com/slurm/ Fri, 24 Jan 2014 14:58:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/slurm <p>SLURM is short for ‘Simple Linux Utility for Resource Management’. It helps you to make use of a <abbr title="a data center ... many computers">cluster</abbr> by giving you a command line interface to add jobs to a queue. That means, you and other users can specify program calls that get executed as soon als all conditions are met.</p> <p>I currently need to work with this, because I have some pretty heavy tasks that occur periodically, but don’t need to be executed immediately. More concrete, I am working in the field of ASR - Automatic Speech Recognition. In ASR you have models that include probabilities for … well, let’s don’t get into detail for that. The important part is that those models need to be trained. And they can get adapted to speakers.</p> <p>As soon as you have more recordings, you can try to improve the model. And this training involves a lot of computation and data processing. As the training job is executed periodically, but not always when a new recording is present, you might also have recordings for many different speakers. So you can improve many models when this script is started. So this can be done on different computers in parallel.</p> <h2 id="slurm-basic-usage">SLURM basic usage</h2> <p>A simple call could look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>srun python test.py -aflag -param value </pre></div> </div> </div> <p>Other notable commands are:</p> <ul> <li><code>squeue</code>: Gives a list of all running / pending jobs</li> <li><code>sbatch</code>: Run a batch script in background</li> <li><code>scancel</code>: Stop a job</li> </ul> <p>Important parameters for <code>srun</code> are:</p> <ul> <li><code>--mem=[X in MB]</code></li> <li><code>--job-name=[Name of your SLURM job]</code></li> <li><code>--dependency</code>: Start this job when all dependencies are met. This could be time or other jobs</li> </ul> <p>Another important command is <code>squeue</code>. It allows you to list all jobs in command line (if you have a GUI: <code>sview</code>).</p> <p>You can get your jobs only with <code>squeue -u mthoma</code>, where <code>mthoma</code> should be replaced by your user name.</p> <h2 id="help-texts">Help texts</h2> <h3 id="sbatch">sbatch</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sbatch --help Usage: sbatch [OPTIONS...] executable [args...] Parallel run options: -A, --account=name charge job to specified account --begin=time defer job until HH:MM MM/DD/YY -c, --cpus-per-task=ncpus number of cpus required per task --comment=name arbitrary comment -d, --dependency=type:jobid defer job until condition on jobid is satisfied -D, --workdir=directory set working directory for batch script -e, --error=err file for batch script's standard error --export[=names] specify environment variables to export --get-user-env load environment from local cluster --gid=group_id group ID to run job as (user root only) --gres=list required generic resources -H, --hold submit job in held state -i, --input=in file for batch script's standard input -I, --immediate exit if resources are not immediately available --jobid=id run under already allocated job -J, --job-name=jobname name of job -k, --no-kill do not kill job on node failure -L, --licenses=names required license, comma separated -m, --distribution=type distribution method for processes to nodes (type = block|cyclic|arbitrary) -M, --clusters=names Comma separated list of clusters to issue commands to. Default is current cluster. Name of 'all' will submit to run on all clusters. --mail-type=type notify on state change: BEGIN, END, FAIL or ALL --mail-user=user who to send email notification for job state changes -n, --ntasks=ntasks number of tasks to run --nice[=value] decrease secheduling priority by value --no-requeue if set, do not permit the job to be requeued --ntasks-per-node=n number of tasks to invoke on each node -N, --nodes=N number of nodes on which to run (N = min[-max]) -o, --output=out file for batch script's standard output -O, --overcommit overcommit resources -p, --partition=partition partition requested --propagate[=rlimits] propagate all [or specific list of] rlimits --qos=qos quality of service -Q, --quiet quiet mode (suppress informational messages) --requeue if set, permit the job to be requeued -t, --time=minutes time limit --time-min=minutes minimum time limit (if distinct) -s, --share share nodes with other jobs --uid=user_id user ID to run job as (user root only) -v, --verbose verbose mode (multiple -v's increase verbosity) Constraint options: --contiguous demand a contiguous range of nodes -C, --constraint=list specify a list of constraints -F, --nodefile=filename request a specific list of hosts --mem=MB minimum amount of real memory --mincpus=n minimum number of logical processors (threads) per node --reservation=name allocate resources from named reservation --tmp=MB minimum amount of temporary disk -w, --nodelist=hosts... request a specific list of hosts -x, --exclude=hosts... exclude a specific list of hosts Consumable resources related options: --exclusive allocate nodes in exclusive mode when cpu consumable resource is enabled --mem-per-cpu=MB maximum amount of real memory per allocated cpu required by the job. --mem &gt;= --mem-per-cpu if --mem is specified. Affinity/Multi-core options: (when the task/affinity plugin is enabled) -B --extra-node-info=S[:C[:T]] Expands to: --sockets-per-node=S number of sockets per node to allocate --cores-per-socket=C number of cores per socket to allocate --threads-per-core=T number of threads per core to allocate each field can be 'min' or wildcard '*' total cpus requested = (N x S x C x T) --ntasks-per-core=n number of tasks to invoke on each core --ntasks-per-socket=n number of tasks to invoke on each socket --cpu_bind= Bind tasks to CPUs (see &quot;--cpu_bind=help&quot; for options) --hint= Bind tasks according to application hints (see &quot;--hint=help&quot; for options) --mem_bind= Bind memory to locality domains (ldom) (see &quot;--mem_bind=help&quot; for options) Help options: -h, --help show this help message -u, --usage display brief usage message Other options: -V, --version output version information and exit </pre></div> </div> </div> <h3 id="squeue">squeue</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>squeue --help Usage: squeue [OPTIONS] -A, --account=account(s) comma separated list of accounts to view, default is all accounts -a, --all display jobs in hidden partitions -h, --noheader no headers on output --hide do not display jobs in hidden partitions -i, --iterate=seconds specify an interation period -j, --job=job(s) comma separated list of jobs IDs to view, default is all -l, --long long report -M, --clusters=cluster_name cluster to issue commands to. Default is current cluster. cluster with no name will reset to default. -n, --nodes=hostlist list of nodes to view, default is all nodes -o, --format=format format specification -p, --partition=partition(s) comma separated list of partitions to view, default is all partitions -q, --qos=qos(s) comma separated list of qos's to view, default is all qos's -s, --step=step(s) comma separated list of job steps to view, default is all -S, --sort=fields comma separated list of fields to sort on --start print expected start times of pending jobs -t, --states=states comma separated list of states to view, default is pending and running, '--states=all' reports all states -u, --user=user_name(s) comma separated list of users to view -v, --verbose verbosity level -V, --version output version information and exit Help options: --help show this help message --usage display a brief summary of squeue options </pre></div> </div> </div> <h2 id="more-information">More information</h2> <ul> <li>Manpages: <ul> <li><a href="https://computing.llnl.gov/tutorials/linux_clusters/man/srun.txt">srun</a></li> <li><a href="https://computing.llnl.gov/tutorials/linux_clusters/man/scancel.txt">scancel</a></li> </ul> </li> <li><a href="https://computing.llnl.gov/linux/slurm/quickstart.html">SLURM Quickstart Guide</a></li> <li><a href="https://rc.fas.harvard.edu/kb/high-performance-computing/slurm/">SLURM Overview from Harvard</a></li> </ul> Ruby //martin-thoma.com/ruby/ Wed, 15 Jan 2014 23:11:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ruby <p>I’m currently learning Ruby to improve my Jekyll blog. At the moment, I can’t really say if I like Ruby.</p> <p>Just like PHP and Python, Ruby is implicitly typed. This means you can do the following:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777"># A list</span> a = [<span style="color:#00D">1</span>,<span style="color:#00D">2</span>,<span style="color:#00D">3</span>,<span style="color:#00D">4</span>,<span style="color:#00D">5</span>] <span style="color:#777"># An integer</span> b = <span style="color:#00D">42</span> <span style="color:#777"># A floating point number</span> c = <span style="color:#60E">3.141</span> </pre></div> </div> </div> <p>Ruby is also dynamically typed:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>a = <span style="color:#00D">42</span> a = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">now a is a string!</span><span style="color:#710">&quot;</span></span> </pre></div> </div> </div> <p>One thing that is pretty annoying is the usage of <code>begin ... end</code>. I thought LaTeX was the only “language” in use that had this syntax.</p> <h2>Syntax examples</h2> <h3>If, else if, else</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>a = <span style="color:#00D">1</span> <span style="color:#080;font-weight:bold">if</span> a == <span style="color:#00D">1</span> || a % <span style="color:#00D">2</span> == <span style="color:#00D">0</span> puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a equals 1 or is even</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">elsif</span> a == <span style="color:#00D">3</span> puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a equals 3</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">else</span> puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a does not equal 1 or 3 and is not even</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">end</span> </pre></div> </div> </div> <h3>String manipulation</h3> <p>String manipulation is weird in Ruby. Take a look at the last example. What would you expect?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>s = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">0123456789</span><span style="color:#710">&quot;</span></span> puts s[<span style="color:#00D">2</span>..<span style="color:#00D">4</span>] puts s[<span style="color:#00D">2</span>..s.length()] puts s[<span style="color:#00D">2</span>..<span style="color:#00D">-2</span>] </pre></div> </div> </div> <p>Output is:</p> <pre><code>234 23456789 2345678 </code></pre> <p>Now what would you expect to happen with <code>"0123456789"[2..4]</code>? I would expect Ruby to give <code>"234"</code>. But this one actually fails.</p> <h3>Dictionaries</h3> <p>Dictionaries, which are sometimes also called ‘maps’ or ‘associative arrays’ are a neat data structure. Ruby uses this syntax:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>dictionary = {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a</span><span style="color:#710">&quot;</span></span>=&gt; <span style="color:#00D">7</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">b</span><span style="color:#710">&quot;</span></span>=&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>} <span style="color:#080;font-weight:bold">if</span> dictionary.has_key?(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a</span><span style="color:#710">&quot;</span></span>) puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">key 'a' is in dictionary! It is </span><span style="color:#710">&quot;</span></span> + dictionary[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a</span><span style="color:#710">&quot;</span></span>].to_s dictionary[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a</span><span style="color:#710">&quot;</span></span>] = <span style="color:#00D">42</span> puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Now it is </span><span style="color:#710">&quot;</span></span> + dictionary[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a</span><span style="color:#710">&quot;</span></span>].to_s puts dictionary.size() puts dictionary.length() puts dictionary.count() <span style="color:#080;font-weight:bold">end</span> </pre></div> </div> </div> <h3>map</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>myList = [<span style="color:#00D">1</span>,<span style="color:#00D">2</span>,<span style="color:#00D">3</span>,<span style="color:#00D">4</span>,<span style="color:#00D">5</span>] x = myList.map{|element| [element,element+<span style="color:#00D">1</span>]} x.each <span style="color:#080;font-weight:bold">do</span> |a, b| puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a: </span><span style="color:#710">&quot;</span></span> + a.to_s + <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">, b: </span><span style="color:#710">&quot;</span></span> + b.to_s <span style="color:#080;font-weight:bold">end</span> </pre></div> </div> </div> <p>will print</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>a: 1, b: 2 a: 2, b: 3 a: 3, b: 4 a: 4, b: 5 a: 5, b: 6 </pre></div> </div> </div> <h3>.count(), .length(), .size()</h3> <p>At a first glance, those three seem to be aliases. But <code>.count()</code> is not quite the same as <code>.length()</code> and <code>.size()</code> (<a href="http://stackoverflow.com/a/4550797/562769">source</a>).</p> <h3>Blocks</h3> <p>A very interesting idea in Ruby is that of blocks. It seems to be similar to Pythons decorators:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">time_method</span>(method=<span style="color:#069">nil</span>, *args) beginning_time = <span style="color:#036;font-weight:bold">Time</span>.now <span style="color:#080;font-weight:bold">if</span> block_given? <span style="color:#080;font-weight:bold">yield</span> <span style="color:#080;font-weight:bold">else</span> <span style="color:#069">self</span>.send(method, args) <span style="color:#080;font-weight:bold">end</span> end_time = <span style="color:#036;font-weight:bold">Time</span>.now puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Time elapsed </span><span style="background-color:hsla(0,0%,0%,0.07);color:black"><span style="font-weight:bold;color:#666">#{</span>(end_time - beginning_time)*<span style="color:#00D">1000</span><span style="font-weight:bold;color:#666">}</span></span><span style="color:#D20"> milliseconds</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">end</span> time_method <span style="color:#080;font-weight:bold">do</span> (<span style="color:#00D">1</span>..<span style="color:#00D">10000</span>).each { |i| i } <span style="color:#080;font-weight:bold">end</span> </pre></div> </div> </div> <h2 id="logging">Logging</h2> <p>Logging in Ruby is very convenient. See <a href="http://www.ruby-doc.org/stdlib-2.1.1/libdoc/logger/rdoc/Logger.html">Logger Documentation</a></p> <h2 id="notable-libraries-and-projects">Notable libraries and projects</h2> <h3 id="nokogiri-parsing-html">Nokogiri: Parsing HTML</h3> <p>The following code will parse <code>yourHTMLcode</code> and select all <code>a</code>-tags (also known as links):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>require <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">nokogiri</span><span style="color:#710">'</span></span> doc = <span style="color:#036;font-weight:bold">Nokogiri</span>::<span style="color:#036;font-weight:bold">HTML</span>.parse(yourHTMLcode) links = doc.css(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">a</span><span style="color:#710">'</span></span>).map { |link| [link[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">href</span><span style="color:#710">'</span></span>],link.text] } links.each <span style="color:#080;font-weight:bold">do</span> |link, linktext| puts <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Link '</span><span style="color:#710">&quot;</span></span>+link+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">' was used with '</span><span style="color:#710">&quot;</span></span>+linktext+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">'</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">end</span> </pre></div> </div> </div> <h3 id="sequel">Sequel</h3> <p>This way you can select elements from a SQLite-Database:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>require <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">sequel</span><span style="color:#710">'</span></span> db = <span style="color:#036;font-weight:bold">Sequel</span>.sqlite(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">search.db</span><span style="color:#710">&quot;</span></span>) rows = db.fetch( <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">SELECT rowid FROM pages WHERE url='/imprint';</span><span style="color:#710">&quot;</span></span> ).all <span style="color:#777">#puts rows</span> <span style="color:#777">#puts rows.count()</span> puts rows[<span style="color:#00D">0</span>][<span style="color:#A60">:rowid</span>] </pre></div> </div> </div> <p>See also:</p> <ul> <li><a href="http://ruby.bastardsbook.com/chapters/html-parsing/">ruby.bastardsbook.com/chapters/html-parsing</a></li> <li><a href="http://nokogiri.org/">nokogiri.org</a></li> <li><a href="https://github.com/styleguide/ruby">Style Guide</a></li> </ul> Sum of cubed digits riddle //martin-thoma.com/sum-of-cubed-digits-riddle/ Sat, 04 Jan 2014 14:53:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sum-of-cubed-digits-riddle <p>Let <code>$N \in \mathbb{N}$</code> be a number with digits <code>$a_k$</code>, where <code>$a_0$</code> is the least significant digit and <code>$n$</code> is the most significant digit.</p> <p>Find all numbers with the following property:</p> <p><code> $$N = \sum_{k=0}^n a_k \cdot 10^k = \sum a_k^3$$</code></p> <h1 id="lower-and-upper-bounds">Lower and upper bounds</h1> <ul> <li>The lower bound is <code>$0$</code></li> <li>The upper bound is <code>$2916$</code> since <code>$4\cdot 9^3 = 2916$</code></li> </ul> <p>You can find better upper bounds, but as we’ve just reduced the possible number space to only 2917 numbers, it doesn’t really matter.</p> <h1 id="find-all-solutions">Find all solutions</h1> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python3</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">find_sum_of_cubes</span>(): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Returns all numbers N with the following property</span><span> </span><span> N = </span><span>\s</span><span>um_{k=0}^n a_k </span><span>\c</span><span>dot 10^k = </span><span>\s</span><span>um a_k^3</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">has_sum_of_cubes_property</span>(n): digits = <span style="color:#369;font-weight:bold">map</span>(<span style="color:#369;font-weight:bold">int</span>, <span style="color:#369;font-weight:bold">list</span>(<span style="color:#369;font-weight:bold">str</span>(n))) <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">sum</span>(<span style="color:#369;font-weight:bold">map</span>(<span style="color:#080;font-weight:bold">lambda</span> n: n**<span style="color:#00D">3</span>, digits)) == n <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">list</span>(<span style="color:#369;font-weight:bold">filter</span>(has_sum_of_cubes_property, <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">2917</span>))) <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: print(find_sum_of_cubes()) </pre></div> </div> </div> <p>which gives</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[0, 1, 153, 370, 371, 407] </pre></div> </div> </div> How to use Jekyll with GitHub //martin-thoma.com/jekyll-and-git/ Mon, 09 Dec 2013 00:00:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/jekyll-and-git <p>You’ve probably noticed that I didn’t write any posts the last few weeks. The reason is that I’ve migrated my WordPress Blog to Jekyll. This means it takes some source files and generates purely static pages from that. The generation process is independant of user requests.</p> <p><a href="http://jekyllrb.com/">Jekyll</a> is a static blog generator, just like <a href="http://blog.getpelican.com/">Pelican</a>, <a href="http://ringce.com/hyde">Hyde</a>, <a href="http://nanoc.ws/">nanoc</a> and <a href="http://octopress.org/">Octopress</a>.</p> <p>I’ve spend about 40-80 hours to migrate from WordPress to Jekyll. And I’m not done jet.</p> <h2 id="jekyll-compared-with-wordpress">Jekyll compared with WordPress</h2> <p>Jekyll is a static site generator. This means you have the source files on your computer. Then you generate the website with Jekyll and upload only the generated files. So you only push content to the server, but you don’t have to download anything from the server.</p> <p>Reasons for Jekyll:</p> <ul> <li><strong>Security</strong>: With Jekyll, you only upload static files (HTML, CSS, JavaScript, Images, …). There is nothing where the user can pass some data. This also means there is one thing less to update.<br /> Assuming your provider updates your server software (e.g. Apache) you don’t have to update anything. In contrast, when you don’t regularly install updates on your WordPress blog (and hope that those updates don’t break anything), your blog is quite likely to be hacked.</li> <li><strong>Speed</strong>: The webserver needs only to serve the sites. Nothing else. Of course, when you use caching with PHP you might get into a similar situation with WordPress. But it will never be faster.</li> <li><strong>Hosting</strong>: You only need webspace. This reduces hosting cost significantly. Additionally, you can use <a href="http://aws.amazon.com/s3/">Amazon S3</a> for hosting!</li> <li><strong>Backups</strong>: Creating security backups is VERY easy with Jekyll. Every tool that can make bakups of files can backup your Jekyll blog. No need to worry about databases. If a file is corrupt, only that file is affected. No worries about maximum execution time for importing / exporting backups. No need to get SSH access. Simple FTP access does the job.</li> </ul> <p>Reasons for WordPress:</p> <ul> <li><strong>Comments</strong>: There is no way to get comments only with static pages. So you need something else, e.g. <a href="http://disqus.com/">disqus</a>.</li> <li><strong>Search</strong>: Could probably be done with JavaScript, but I guess it is difficult.</li> <li><strong>Editor</strong>: WordPress gives you a WYSIWYG editor. I don’t know if there is something similar for Jekyll.</li> <li><strong>Compile time</strong>: Compilation time is very long for Jekyll. For my blog, it needs over 6 minutes. As I test the result quite often before I publish posts, this is very annoying.</li> <li><strong>Tagging, Category pages, Author pages</strong>: Currently, Jekyll lacks basic support for blogging. You don’t have tag pages per default, the plugins that provide tags don’t have paginated tag index pages. The same problem occurs when it comes to categories or authors.</li> <li><strong>Timed posts</strong>: I did not use timed posts very often, but it is very easy to create them with WordPress. With Jekyll, on the other hand, you have to know how to create cronjobs. And your computer has to be running.</li> </ul> <h2 id="install-jekyll">Install Jekyll</h2> <p>On an Ubunty system I need for this blog:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo apt-get install ruby1.9.1-dev imagemagick ruby-rmagick libmagickwand-dev ruby-execjs ruby-nokogiri $ sudo gem install jekyll $ sudo gem install dimensions $ sudo gem install fileutils $ sudo mkdir -p /var/www/blog </pre></div> </div> </div> <h2 id="github">GitHub</h2> <h3 id="create-your-repository">Create your repository</h3> <ol> <li>Go to <a href="https://github.com/">github.com</a>, sign in and create a new repo:</li> <li>Call it <code>[Username].github.io</code>.</li> </ol> <h3 id="branches">Branches</h3> <p>The way to use Jekyll with GitHub is by using branches. Go to your Git repository that cointains your blog:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc08 ~/Downloads/MartinThoma.github.io $ ls _config.yml favicon.ico index.html Makefile Readme.md css images js _plugins _site _drafts _includes _layouts _posts thumbs </pre></div> </div> </div> <p>Now you should create a new branch that will contain your source files. The following command creates a branch <code>sources</code> that starts where the branch <code>master</code> currently is:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>git checkout -b source master </pre></div> </div> </div> <p>Now update this branch to the server:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>git push -u origin source </pre></div> </div> </div> <p>When you enter</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>git checkout . master </pre></div> </div> </div> <p>you will switch to the <code>master</code> brach. The same way you can switch to the <code>source</code> branch. After you’ve entered the command, you can look at the folder in your file system. There will only be the data of the current branch.</p> <h3 id="custom-domain">Custom Domain</h3> <p>If you want to host your content at GitHub, but have a custom Domain like <code>martin-thoma.com</code> instead of <code>martinthoma.github.io</code>, you have to:</p> <ol> <li>Ask your provider (in my case “Knallhart”) to add an A-record to Github.</li> <li>Add a file called <code>CNAME</code> with content <code>martin-thoma.com</code> (yes, without <code>http://</code>) to the root of your directory</li> </ol> <p>GitHub also offers some help on <a href="https://help.github.com/articles/setting-up-a-custom-domain-with-pages">setting up a custom domain with Pages</a>.</p> <h2 id="ftp-server">FTP Server</h2> <p>If you have your own FTP server, you probably want to use it.</p> <p>One tool that might now come to your mind is <code>rsync</code>. But rsync needs SSH (<a href="http://serverfault.com/a/24627/113899">source</a>). If you have SSH, then you can do something like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>rsync -avz --delete _site/ user@host:/path/to/web/root </pre></div> </div> </div> <p>The <code>--delete</code> options “delete[s] extraneous files from dest dirs”, <code>-a</code> means archive which preserves the owner, group, change date and some more of files, <code>-v</code> is verbose as always and <code>-z</code> is for compression while the file transfer happens. <code>--progress</code> might also be interesting, especially for the first upload.</p> <p>Otherwise, you might want to try <code>curlftpfs</code>. This program lets you mount a FTP folder:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>curlftpfs ftp.example.com/backups /mnt/ftpserver </pre></div> </div> </div> <p>and you can also umount it:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>rsync --delete /var/backups /mnt/ftpserver </pre></div> </div> </div> <h2 id="markdown">Markdown</h2> <p>I’ve switched between <code>rdiscount</code> and <code>redcarpet</code>. The former is faster, the latter supports fenced code blocks. I finally stuck with redcarped, because Liquid has problems when it comes to C++ for loops after curly braces.</p> <p>Other Markdown parsers are <code>maruku</code> (which has a <a href="https://github.com/bhollis/maruku/issues/121">Multiple lines for HTML &lt;li&gt;-tag</a> issue) and <code>kramdown</code> (which is slow and does not handle fenced code blocks and LaTeX correctly).</p> <p>Similar to <a href="http://bloerg.net/2013/03/07/using-kramdown-instead-of-maruku.html">Matthias</a> I would like to share a feature matrix of Markdown parsers included into Jekyll. I have used <code>jekyll 1.4.3</code> to create the following table. I’ve used <a href="../formatting-strings-python/">this page</a> to see if fenced code blocks and pygments is working and <a href="../solve-linear-congruence-equations/">that page</a> for LaTeX. Everything was tested with <a href="https://github.com/MartinThoma/MartinThoma.github.io">this site</a>.</p> <table> <thead> <tr> <th> </th> <th><code>redcarpet</code></th> <th><code>rdiscount</code></th> <th><code>kramdown</code></th> <th><code>maruku</code></th> </tr> </thead> <tbody> <tr> <td>LaTeX</td> <td>✓</td> <td>✓</td> <td>✓</td> <td>?</td> </tr> <tr> <td>Fenced code blocks</td> <td>✓</td> <td>✓</td> <td>~</td> <td>?</td> </tr> <tr> <td>Pygments</td> <td>✓</td> <td>✓</td> <td>✓</td> <td>?</td> </tr> <tr> <td>Site generation</td> <td>176.90s</td> <td>165.41s</td> <td>293.26s</td> <td>?</td> </tr> </tbody> </table> <p>Kramdown destroyed some fenced code blocks (but not all) and maruku did not even compile my site at all.</p> <h3 id="linebreaks-and-newline">Linebreaks and newline</h3> <p>Linebreaks are an issue. Sometimes I want to get a <code>&lt;br/&gt;</code>, sometimes I make linebreaks to make reading of the text files easier. It’s basically <a href="http://meta.stackoverflow.com/questions/26011/should-the-markdown-renderer-treat-a-single-line-break-as-br">this discussion</a>.</p> <p>Currently, I’m not satisfied with the situation. I never had that problem with WordPress. WordPress simply created paragraphs just at the right location.</p> <h2 id="customization">Customization</h2> <p>You can create <a href="http://jekyllrb.com/docs/plugins/">custom Liquid filters</a>, plugins and templates. Everything is quite easy. The Liquid templating language seems to be very similar to Django Templates (Python).</p> <h2 id="make-the-website-super-fast">Make the Website super-fast</h2> <h3 id="css-minification">CSS Minification</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo gem install juicer juicer install jslint juicer install yui_compressor </pre></div> </div> </div> <h3 id="images">Images</h3> <p>I’ve included small images as base64 (used <a href="http://webcodertools.com/imagetobase64converter/Create">this online tool</a>). According to <a href="http://caniuse.com/datauri">caniuse</a> it’s quite save to use.</p> <h2 id="site-search">Site Search</h2> <p>Site search is a real problem. I’ve seen three solutions so far:</p> <ol> <li><strong>Dynamic Search</strong>: You can add a dynamic part to your statically generated website. For example, I create a <code>search/index.php</code> and a SQLite database like it was <a href="http://www.businessguide.co.uk/blog/jekyll-search-ways-to-search-a-static-site/">described here</a>.</li> <li><strong>Static JavaScript</strong>: Create a JSON file or something similar and search dynamically with JavaScript in it.</li> <li><strong>External Search Engines</strong>: You could use a search engine for searching your site, of course. <ul> <li>Hosted by you:</li> <li>Commercial <ul> <li><a href="https://www.google.com/cse">Google Custom Search</a></li> <li><a href="http://www.indexden.com/">Index Den</a>: Has no direct support to parse your website</li> </ul> </li> </ul> </li> </ol> <h3 id="phpsqlite">PHP+SQLite</h3> <h3 id="javascript-solutions">JavaScript solutions</h3> <p>One JavaScript solution I’ve found is <a href="https://github.com/slashdotdash/jekyll-lunr-js-search">lunr</a>. This one is really bad as it copies the whole body to a json file. This json file has to be loaded before it works. But my posts total at the moment to 2MB. I’m pretty sure my readers don’t want to wait until 2MB are downloaded. So this one does only work for smaller websites.</p> <p><a href="http://christian-fei.com/simple-jekyll-search-jquery-plugin/">Christan Fei’s solution</a> does only search in the title and category.</p> <h2 id="templates">Templates</h2> <p>Jekyll uses Liquid as a templating language. It is similar to Django templates. <a href="https://github.com/Shopify/liquid/wiki/Liquid-for-Designers">Here</a> is a short introduction to Liquid.</p> <p>A Sublime Text template is the following:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&lt;snippet&gt; &lt;content&gt;&lt;![CDATA[ --- layout: post title: ${1:} author: Martin Thoma date: 2014-11-22 17:19 categories: - ${2:Cyberculture} tags: - ${3:Rating} featured_image: logos/${4:star.png} --- ${5:} ]]&gt;&lt;/content&gt; &lt;!-- Optional: Set a tabTrigger to define how to trigger the snippet --&gt; &lt;tabTrigger&gt;---&lt;/tabTrigger&gt; &lt;!-- Optional: Set a scope to limit where the snippet will trigger --&gt; &lt;!-- &lt;scope&gt;source.python&lt;/scope&gt; --&gt; &lt;/snippet&gt; </pre></div> </div> </div> <h2 id="some-tests">Some tests</h2> <ul> <li>Validation <ul> <li><a href="http://validator.w3.org/check?uri=martin-thoma.com">validator.w3.org</a>: My site is HTML-valid. The error that this validator shows is caused by an bug inside of the validator itself.</li> <li><a href="http://jigsaw.w3.org/css-validator/validator?uri=martin-thoma.com">jigsaw.w3.org</a>: My site is CSS-valid.</li> </ul> </li> <li>Speed: Could be better… <ul> <li><a href="http://tools.pingdom.com/">tools.pingdom.com</a></li> <li><a href="http://developers.google.com/speed/pagespeed/insights/?url=martin-thoma.com">PageSpeed</a> 72 on mobile and 85 on desktop</li> </ul> </li> <li>Accessiblity: <ul> <li><a href="http://wave.webaim.org/report#/http%3A%2F%2Fmartin-thoma.com%2F">wave.webaim.org</a></li> <li><a href="http://fae.cita.uiuc.edu/report/14396f38bc6546f6/">Functional Accessibility Evaluator</a></li> </ul> </li> <li>More: <ul> <li><a href="http://ready.mobi/launch.jsp?locale=en_EN#fragment-1">Mobile readyness</a></li> <li><a href="http://loadimpact.com/">Load test</a></li> <li><a href="http://www.alexa.com/siteinfo/martin-thoma.com">Alexa</a></li> <li><a href="http://www.google.com/webmasters/tools/richsnippets">Google Structured Data Testing Tool</a>: Test if google can extract the author from your blog posts</li> <li><a href="https://dev.twitter.com/docs/cards/validation/validator">Twitter card validator</a> (more about <a href="https://dev.twitter.com/cards">Twitter cards</a>)</li> <li><a href="http://nibbler.silktide.com/reports/martin-thoma.com">Nibbler</a>: This one tests quite a lot.</li> </ul> </li> </ul> <p>I’ve also used LinkChecker to check if all new links are valid. I’ve found quite a lot of old links and replaced them with new links.</p> <h2 id="resources">Resources</h2> <ul> <li><a href="https://help.github.com/articles/setting-up-a-custom-domain-with-pages#setting-the-domain-in-your-repo">Setting up a custom domain with Pages</a></li> <li><a href="https://alybadawy.com/developing/2013/08/02/search-a-jekyll-generated-website/">Search a Jekyll-generated website</a></li> <li><a href="http://philipm.at/2011/jekyll_vs_hyde.html">Jekyll vs. Hyde - A Comparison Of Two Static Site Generators</a></li> </ul> How to check if a point is inside of a polygon? //martin-thoma.com/check-point-inside-polygon/ Mon, 18 Nov 2013 21:36:09 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/check-point-inside-polygon <p>Suppose you have a with <code>$n$</code> sides. This is called a <code>$n$</code>-glon.</p> <h2>Basics about polygones</h2> <p>A <code>$n$</code>-glon can be defined by a list of <code>$n$</code> points.</p> <p>Note that the order is important:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/11/polygon-order.png"><img src="../images/2013/11/polygon-order.png" alt="The order of points is important for the definition of a polygon" width="" height="" class="" /></a><p class="wp-caption-text">[A, B, C, D, E, F, G] != [A, B, C, D, F, E, G]</p></div> <p>I will not consider self-intersecting polygones for the following statements. I’m aware of them, but whenever you have a self-intersecting polygon you can create multiple polygones that cover the same area and don’t intersect each other (some pairs might have a finite number of points in common, but not an infinite number).</p> <h2>Is a point in a triangle / a rectangle</h2> <p>It is quite easy to check weather a point is inside of a triangle or inside of a rectangle. I have already written an article about <a href="../how-to-check-if-a-point-is-inside-a-rectangle/">how to check if a point is inside of a rectangle</a>.</p> <h2>Is a point inside of a n-glon?</h2> <p>Let <code>$P$</code> be a point and <code>$N = [P_1, P_2, \dots, P_n]$</code> be a <code>$n$</code>-glon. It is now much more difficult to check if <code>$P$</code> is inside of <code>$N$</code>. The area-approach works for convex <code>$n$</code>-glons, but that’s it.</p> <h3>Count Crossing Line Segments</h3> <p>However, you can try another approach which I have visualized in the following image:</p> <div style="width: 522px" class="wp-caption "><a href="../images/2013/11/polygon-is-point-inside.png"><img src="../images/2013/11/polygon-is-point-inside.png" alt="Check if P is inside of N" width="" height="" class="size-full wp-image-76730" /></a><p class="wp-caption-text">Check if P is inside of N</p></div> <p>When <code>$P$</code> is inside of <code>$N$</code>, every line <code>$P_{1}P, P_{2}P, \dots, P_{n}P$</code> will cross the polygon lines <code>$P_{1}P_2,P_{2}P_3, \dots, P_{n}P_1$</code> an even number of times. If P is outside, at least one of the lines <code>$P_{i}P$</code> will cross a polygon line <code>$P_{j}P_{j+1}$</code> once.</p> <p>This means, for every check you have to check <code>$n^2$</code> pairs of line segments for crossings. How you can do that is explained in my article <a href="../how-to-check-if-two-line-segments-intersect/" title="How to check if two line segments intersect">How to check if two line segments intersect</a>.</p> <p>This algorithm is in <code>$\mathcal{O}(n^2)$</code> time complexity (it does need a constant amount of additional space).</p> <h3>Triangularization</h3> <p>When you have a lot of querys, you might want to divide your polygon into convex polygones. The easiest way to do this might be dividing <code>$N$</code> into triangles.</p> <p>That way, you can check for every triangle if <code>$P$</code> is inside of it. I assume that the number of triangles is not bigger than <code>$n$</code>. As the check is in constant time for one triangle, you would have an algorithm that needs <code>$\mathcal{O}(n)$</code> time and space for its checks (+ some preprocessing which is done only once).</p> Word Error Rate Calculation //martin-thoma.com/word-error-rate-calculation/ Fri, 15 Nov 2013 08:59:15 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/word-error-rate-calculation <p>The Word Error Rate (short: WER) is a way to measure performance of an <abbr title="Automatic Speech Recognizer">ASR</abbr>. It compares a reference to an hypothesis and is defined like this:</p> <p>[\mathit{WER} = \frac{S+D+I}{N}]</p> <p>where</p> <ul> <li>S is the number of substitutions,</li> <li>D is the number of deletions,</li> <li>I is the number of insertions and</li> <li>N is the number of words in the reference</li> </ul> <h2 id="examples">Examples</h2> <pre>REF: What a bright day HYP: What a day</pre> <p>In this case, a deletion happened. “Bright” was deleted by the ASR.</p> <pre>REF: What a day HYP: What a bright day</pre> <p>In this case, an insertion happened. “Bright” was inserted by the ASR.</p> <pre>REF: What a bright day HYP: What a light day</pre> <p>In this case, an substitution happened. “Bright” was substituted by “light” by the ASR.</p> <h2 id="range-of-values">Range of values</h2> <p>As only addition and division with non-negative numbers happen, WER cannot get negativ. It is 0 exactly when the hypothesis is the same as the reference.</p> <p>WER can get arbitrary large, because the ASR can insert an arbitrary amount of words.</p> <h2>Calculation</h2> <p>Interestingly, the WER is just the Levenshtein distance for words.</p> <p>I’ve understood it after I saw this on the German Wikipedia:</p> <p>[ \begin{align} m &amp;= |r|<br /> n &amp;= |h|<br /> \end{align} ]</p> <p>[ \begin{align} D_{0, 0} &amp;= 0<br /> D_{i, 0} &amp;= i, 1 \leq i \leq m<br /> D_{0, j} &amp;= j, 1 \leq j \leq n \end{align}]</p> <p>[ \text{For } 1 \leq i\leq m, 1\leq j \leq n<br /> D_{i, j} = \min \begin{cases} D_{i - 1, j - 1}&amp;+ 0 \ {\rm if}\ u_i = v_j<br /> D_{i - 1, j - 1}&amp;+ 1 \ {\rm(Replacement)} <br /> D_{i, j - 1}&amp;+ 1 \ {\rm(Insertion)} <br /> D_{i - 1, j}&amp;+ 1 \ {\rm(Deletion)} \end{cases} ]</p> <p>But I have written a piece of pseudocode to make it even easier to code this algorithm:</p> <div style="width: 510px" class="wp-caption "><a href="../images/2013/11/WER-calculation.png"><img src="../images/2013/11/WER-calculation.png" alt="WER calculation" width="" height="" class="size-full wp-image-76716" /></a><p class="wp-caption-text">WER calculation</p></div> <h2>Python</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="k">def</span> <span class="nf">wer</span><span class="p">(</span><span class="n">r</span><span class="p">,</span> <span class="n">h</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;</span> <span class="sd"> Calculation of WER with Levenshtein distance.</span> <span class="sd"> Works only for iterables up to 254 elements (uint8).</span> <span class="sd"> O(nm) time ans space complexity.</span> <span class="sd"> &gt;&gt;&gt; wer(&quot;who is there&quot;.split(), &quot;is there&quot;.split())</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; wer(&quot;who is there&quot;.split(), &quot;&quot;.split())</span> <span class="sd"> 3</span> <span class="sd"> &gt;&gt;&gt; wer(&quot;&quot;.split(), &quot;who is there&quot;.split())</span> <span class="sd"> 3</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="c"># initialisation</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="n">d</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">zeros</span><span class="p">((</span><span class="nb">len</span><span class="p">(</span><span class="n">r</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">*</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">h</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">),</span> <span class="n">dtype</span><span class="o">=</span><span class="n">numpy</span><span class="o">.</span><span class="n">uint8</span><span class="p">)</span> <span class="n">d</span> <span class="o">=</span> <span class="n">d</span><span class="o">.</span><span class="n">reshape</span><span class="p">((</span><span class="nb">len</span><span class="p">(</span><span class="n">r</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">h</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">))</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">r</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">h</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">i</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">d</span><span class="p">[</span><span class="mi">0</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">j</span> <span class="k">elif</span> <span class="n">j</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="n">i</span> <span class="c"># computation</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">r</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">h</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">r</span><span class="p">[</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">==</span> <span class="n">h</span><span class="p">[</span><span class="n">j</span><span class="o">-</span><span class="mi">1</span><span class="p">]:</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="n">j</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="k">else</span><span class="p">:</span> <span class="n">substitution</span> <span class="o">=</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="n">j</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="mi">1</span> <span class="n">insertion</span> <span class="o">=</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="mi">1</span> <span class="n">deletion</span> <span class="o">=</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+</span> <span class="mi">1</span> <span class="n">d</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="n">substitution</span><span class="p">,</span> <span class="n">insertion</span><span class="p">,</span> <span class="n">deletion</span><span class="p">)</span> <span class="k">return</span> <span class="n">d</span><span class="p">[</span><span class="nb">len</span><span class="p">(</span><span class="n">r</span><span class="p">)][</span><span class="nb">len</span><span class="p">(</span><span class="n">h</span><span class="p">)]</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">doctest</span> <span class="n">doctest</span><span class="o">.</span><span class="n">testmod</span><span class="p">()</span></code></pre></div> <h2>Explanation</h2> <p>No matter at what stage of the code you are, the following is always true:</p> <ul> <li>If <code>r[i]</code> equals <code>h[j]</code> you don't have to change anything. The error will be the same as it was for <code>r[:i-1]</code> and <code>h[:j-1]</code></li> <li>If its a substitution, you have the same number of errors as you had before when comparing the <code>r[:i-1]</code> and <code>h[:j-1]</code></li> <li>If it was an insertion, then the hypothesis will be longer than the reference. So you can delete one from the hypothesis and compare the rest. As this is the other way around for deletion, you don't have to worry when you have to delete something.</li> </ul> Formatting Strings in Python //martin-thoma.com/formatting-strings-python/ Thu, 07 Nov 2013 20:05:33 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/formatting-strings-python <p>In Python, you can use the following ways to format Strings:</p> <h2 id="print-directly">Print directly</h2> <p>Printing them directly (just like <a href="http://www.cplusplus.com/reference/cstdio/printf/">printf in C</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>birthday = <span style="color:#00D">28</span> month = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">April</span><span style="color:#710">&quot;</span></span> year = <span style="color:#00D">1990</span> print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">My birthday is the %i-th %s %i.</span><span style="color:#710">&quot;</span></span> % (birthday, month, year)) </pre></div> </div> </div> <p>The first string contains the rules how to format. <code>%i</code> means that the first argument in the following tuple should be interpreted as a integer. The second one <code>%s</code> should be interpreted as a string and the third one again as a integer.</p> <h2 id="save-as-string">Save as string</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt;&gt; a = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Why is %i the answer?</span><span style="color:#710">&quot;</span></span> % <span style="color:#00D">42</span> &gt;&gt;&gt; a <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Why is 42 the answer?</span><span style="color:#710">'</span></span> </pre></div> </div> </div> <h2 id="named-formatting">Named formatting</h2> <p>You might prefer named formatting:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt;&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">{guy} loves {girl}.</span><span style="color:#710">&quot;</span></span>.format(girl=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Marie</span><span style="color:#710">&quot;</span></span>, guy=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Martin</span><span style="color:#710">&quot;</span></span>) <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Martin loves Marie.</span><span style="color:#710">'</span></span> </pre></div> </div> </div> <p>You can also store this first in a dictionary an unpack it:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt;&gt; myDictionary = {<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">girl</span><span style="color:#710">&quot;</span></span>:<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Marie</span><span style="color:#710">&quot;</span></span>,<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">guy</span><span style="color:#710">&quot;</span></span>: <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Martin</span><span style="color:#710">&quot;</span></span>,<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">other</span><span style="color:#710">&quot;</span></span>:<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Internet</span><span style="color:#710">&quot;</span></span>} &gt;&gt;&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">{guy} loves {girl}.</span><span style="color:#710">&quot;</span></span>.format(girl=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Marie</span><span style="color:#710">&quot;</span></span>, guy=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Martin</span><span style="color:#710">&quot;</span></span>) <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Martin loves Marie.</span><span style="color:#710">'</span></span> </pre></div> </div> </div> <h2 id="date-and-time">Date and Time</h2> <p>You can format time any way you like, just look at <a href="http://docs.python.org/2/library/datetime.html#strftime-and-strptime-behavior">this reference</a>.</p> <h2>Lists</h2> <p>Question: I would like to print a list! How do I do that? Answer: Convert your list to a string</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>&gt;&gt;&gt; myList = [<span style="color:#00D">1</span>,<span style="color:#00D">2</span>,<span style="color:#00D">3</span>] &gt;&gt;&gt; print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Your list: %s</span><span style="color:#710">&quot;</span></span> % (<span style="color:#369;font-weight:bold">str</span>(myList))) Your <span style="color:#369;font-weight:bold">list</span>: [<span style="color:#00D">1</span>, <span style="color:#00D">2</span>, <span style="color:#00D">3</span>] </pre></div> </div> </div> <h2 id="str-and-repr"><strong>str</strong> and <strong>repr</strong></h2> <p>When you build your own objects, you should add an implementation for the method <code>__str__</code> and <code>__repr__</code>. The first one should return a string representation that is human readable of the object, the second one should return a string that identifies the object.</p> <h2 id="formatters">Formatters</h2> <table> <tr> <td><code>%i</code></td> <td>Integer</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mi">123</span><span class="p">))</span> <span class="mi">123</span></code></pre></div> </td> </tr> <tr> <td><code>%s</code></td> <td>String</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="s">&quot;Martin&quot;</span><span class="p">))</span> <span class="n">Martin</span></code></pre></div> </td> </tr> <tr> <td><code>%o</code></td> <td>Int as octal</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%o</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">123.123</span><span class="p">))</span> <span class="mi">173</span></code></pre></div> </td> </tr> <tr> <td><code>%x</code></td> <td>Int as hexadecimal (lower case)</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%x</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">123.123</span><span class="p">))</span> <span class="mi">7</span><span class="n">b</span></code></pre></div> </td> </tr> <tr> <td><code>%X</code></td> <td>Int as hexadecimal (upper case)</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%X</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">123.123</span><span class="p">))</span> <span class="mi">7</span><span class="n">B</span></code></pre></div> </td> </tr> <tr> <td><code>%f</code></td> <td>Floating point</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%f</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">123.123</span><span class="p">))</span> <span class="mf">123.123000</span></code></pre></div> </td> </tr> <tr> <td><code>%.2f</code></td> <td>Floating point with two decimal places</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%.2f</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">123.123</span><span class="p">))</span> <span class="mf">123.12</span></code></pre></div> </td> </tr> <tr> <td><code>%e</code></td> <td>Floating point in scientific notation</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%e</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">123.123</span><span class="p">))</span> <span class="mf">1.231230e+02</span></code></pre></div> </td> </tr> <tr> <td><code>%%</code></td> <td>Percent sign</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%i%%</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mi">65</span><span class="p">))</span> <span class="mi">65</span><span class="o">%</span></code></pre></div> </td> </tr> <tr> <td><code>%6.2f</code></td> <td>Print a float with 2 decimal places. Add spaces if this has less than 6 characters.</td> <td> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="o">&gt;&gt;&gt;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%6.2f</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="mf">65.123</span><span class="p">))</span> <span class="mf">65.12</span></code></pre></div> </td> </tr> </table> <h2 id="columns">Columns</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>my_list = [(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Easybox 1234</span><span style="color:#710">'</span></span>, <span style="color:#00D">54</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">DC:9F:DB:B2:B1:1C</span><span style="color:#710">'</span></span>), (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">FRITZ!Box 6360 Cable</span><span style="color:#710">'</span></span>, <span style="color:#00D">12</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">24:65:11:06:71:54</span><span style="color:#710">'</span></span>), (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">wkit-802.1x</span><span style="color:#710">'</span></span>, <span style="color:#00D">15</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">A0:D3:C1:9F:FF:11</span><span style="color:#710">'</span></span>)] header = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">&quot;</span><span style="color:#D20">{0:&lt;20}{1:&gt;6}{2:&gt;20}</span><span style="color:#710">&quot;</span></span>.format(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">SSID</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Signal</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">HwAddress</span><span style="color:#710">'</span></span>) print(header) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>*<span style="color:#369;font-weight:bold">len</span>(header)) <span style="color:#080;font-weight:bold">for</span> ssid, signal, hwaddress <span style="color:#080;font-weight:bold">in</span> my_list: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#E40">u</span><span style="color:#710">&quot;</span><span style="color:#D20">{0:&lt;20}{1:&gt;6}{2:&gt;20}</span><span style="color:#710">&quot;</span></span>.format(ssid, <span style="color:#369;font-weight:bold">str</span>(signal)+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">%</span><span style="color:#710">'</span></span>, hwaddress)) </pre></div> </div> </div> <p>results in</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>SSID Signal HwAddress ---------------------------------------------- Easybox 1234 54% DC:9F:DB:B2:B1:1C FRITZ!Box 6360 Cable 12% 24:65:11:06:71:54 wkit-802.1x 15% A0:D3:C1:9F:FF:11 </pre></div> </div> </div> <h2 id="resources">Resources</h2> <ul> <li><a href="http://docs.python.org/2/library/string.html#format-specification-mini-language">Format Specification Mini-Language</a></li> <li><a href="http://docs.python.org/2/library/datetime.html#strftime-and-strptime-behavior">Time formatting</a></li> <li><a href="http://docs.python.org/2/library/pprint.html">Pretty Print</a></li> </ul> Fibonacci, recursion and decorators //martin-thoma.com/fibonacci-recursion-decorators/ Thu, 31 Oct 2013 11:08:01 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/fibonacci-recursion-decorators <p>I think everybody who learned something about recursion has seen the Fibonacci sequence:</p> <p><code>$ f(n) := \begin{cases} n &amp;\text{if } n \leq 1\\ f(n-1) + f(n-2) &amp;\text{otherwise} \end{cases} $</code></p> <p>The simplest solution to get this number is:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="p">:</span> <span class="k">return</span> <span class="n">n</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">2</span><span class="p">)</span></code></pre></div> <p>The problem is, of course, that the number of evaluations goes wild. Here is a table of the number of function calls</p> <table> <tr> <th>n</th> <td>0</td> <td>1</td> <td>2</td> <td>3</td> <td>4</td> <td>5</td> <td>6</td> <td>7</td> <td>8</td> <td>9</td> <td>10</td> <td>20</td> </tr> <tr> <th>calls</th> <td>1</td> <td>1</td> <td>3</td> <td>5</td> <td>9</td> <td>15</td> <td>25</td> <td>41</td> <td>67</td> <td>109</td> <td>177</td> <td>21891</td> </tr> </table> <p>To be exact, the number of calls of the fib-function is:</p> <p><code>$ f(n) := \begin{cases} 1 &amp;\text{if } n \leq 1\\ f(n-1) + f(n-2) + 1 &amp;\text{otherwise} \end{cases} $</code></p> <p>This means the dumb function is in <code>$\mathcal{O}(2^n)$</code>! (I’m not quite sure, but this I think this is not only time complexity, but also space complexity. I think it is not <a href="https://en.wikipedia.org/wiki/Tail_recursion">tail recursive</a>, so the complete stackframe has to be saved.)</p> <h2>Memorization with decorators</h2> <p>One way to solve the problem much faster (in fact in <code>$\mathcal{O}(n)$</code> time and space complexity) by storing values we already calculated.</p> <p>A very neat way to achieve this are decorators. It might be a common problem that you have a recursive, mathematical function with no side effects. So you can write a wrapper that checks if the value has already been calculated. If not, the function proceeds as usual. It it has already been calculated, you can simply look it up:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">memoize</span><span class="p">(</span><span class="n">obj</span><span class="p">):</span> <span class="n">cache</span> <span class="o">=</span> <span class="p">{}</span> <span class="k">def</span> <span class="nf">memoizer</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span> <span class="k">if</span> <span class="n">args</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">cache</span><span class="p">:</span> <span class="n">cache</span><span class="p">[</span><span class="n">args</span><span class="p">]</span> <span class="o">=</span> <span class="n">obj</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">)</span> <span class="k">return</span> <span class="n">cache</span><span class="p">[</span><span class="n">args</span><span class="p">]</span> <span class="k">return</span> <span class="n">memoizer</span> <span class="nd">@memoize</span> <span class="k">def</span> <span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="p">:</span> <span class="k">return</span> <span class="n">n</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">2</span><span class="p">)</span></code></pre></div> <p>Notice that I’ve only added <code>@memoize</code> over the function definiton of <code>fib</code>! I love Python ☺</p> <p>By the way, this formula has also some limitations. Python has a fixed maximum recursion depth. So <code>fib(332)</code> worked fine, but <code>fib(333)</code> gave:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">RuntimeError: maximum recursion depth exceeded in comparison</code></pre></div> <p>You can get around this limitation by successive calls of fib:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c"># Call to fill array</span> <span class="n">fib</span><span class="p">(</span><span class="mi">332</span><span class="p">)</span> <span class="c"># The number of recursive steps is now much smaller:</span> <span class="k">print</span><span class="p">(</span><span class="n">fib</span><span class="p">(</span><span class="mi">500</span><span class="p">))</span></code></pre></div> <p>That gave 139423224561697880139724382870407283950070256587697307264108962948325571622863290691557658876222521294125. A pretty big number.</p> <h2>Formula of Moivre-Binet</h2> <p>The formula of Moivre-Binet gives a closed form for calculating fibonacci numbers:</p> <p><code>$\varphi = \frac{\sqrt{5}+1}{2}$</code> <code>$\psi = 1 - \varphi$</code> <code>$f(n) = \frac{\varphi^n - \psi^n}{\phi - \psi}$</code></p> <p>Although this is mathematically exact, it will not work on computers due to a fixed floating point precision. Lets check how long it works:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="kn">import</span> <span class="nn">functools</span> <span class="k">def</span> <span class="nf">memoize</span><span class="p">(</span><span class="n">obj</span><span class="p">):</span> <span class="n">cache</span> <span class="o">=</span> <span class="p">{}</span> <span class="nd">@functools.wraps</span><span class="p">(</span><span class="n">obj</span><span class="p">)</span> <span class="k">def</span> <span class="nf">memoizer</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span> <span class="k">if</span> <span class="n">args</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">cache</span><span class="p">:</span> <span class="n">cache</span><span class="p">[</span><span class="n">args</span><span class="p">]</span> <span class="o">=</span> <span class="n">obj</span><span class="p">(</span><span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">)</span> <span class="k">return</span> <span class="n">cache</span><span class="p">[</span><span class="n">args</span><span class="p">]</span> <span class="k">return</span> <span class="n">memoizer</span> <span class="nd">@memoize</span> <span class="k">def</span> <span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="p">:</span> <span class="k">return</span> <span class="n">n</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">2</span><span class="p">)</span> <span class="k">def</span> <span class="nf">moivreBinet</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">phi</span> <span class="o">=</span> <span class="p">(</span><span class="mi">5</span><span class="o">**</span><span class="mf">0.5</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span> <span class="n">psi</span> <span class="o">=</span> <span class="mi">1</span> <span class="o">-</span> <span class="n">phi</span> <span class="k">return</span> <span class="nb">int</span><span class="p">((</span><span class="n">phi</span><span class="o">**</span><span class="n">n</span> <span class="o">-</span> <span class="n">psi</span><span class="o">**</span><span class="n">n</span><span class="p">)</span><span class="o">/</span><span class="p">(</span><span class="n">phi</span> <span class="o">-</span> <span class="n">psi</span><span class="p">))</span> <span class="kn">from</span> <span class="nn">itertools</span> <span class="kn">import</span> <span class="n">count</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="n">count</span><span class="p">(</span><span class="mi">0</span><span class="p">):</span> <span class="n">exact</span> <span class="o">=</span> <span class="n">fib</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="n">constTime</span> <span class="o">=</span> <span class="n">moivreBinet</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="k">if</span> <span class="n">exact</span> <span class="o">!=</span> <span class="n">constTime</span><span class="p">:</span> <span class="k">print</span><span class="p">((</span><span class="s">&quot;The </span><span class="si">%i</span><span class="s">-th fibonacci number is </span><span class="si">%i</span><span class="s">. Moivre-Binet &quot;</span> <span class="o">+</span> <span class="s">&quot;gives due to precicion error </span><span class="si">%i</span><span class="s"> (delta=</span><span class="si">%i</span><span class="s">).&quot;</span><span class="p">)</span> <span class="o">%</span> <span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="n">exact</span><span class="p">,</span> <span class="n">constTime</span><span class="p">,</span> <span class="nb">abs</span><span class="p">(</span><span class="n">exact</span><span class="o">-</span><span class="n">constTime</span><span class="p">)))</span> <span class="k">break</span></code></pre></div> <p>So the answer is:</p> <blockquote>The 72-th fibonacci number is 498454011879264. Moivre-Binet gives due to precicion error 498454011879265 (delta=1).</blockquote> <p>This is a reason to prefer the <code>$\mathcal{O}(n)$</code> solution over the <code>$\mathcal{O}(1)$</code> solution. If you’re only exact for 72 numbers, you could also simply store them. Looking number up form an array is always faster than any calculation.</p> <h2>Very high numbers</h2> <p>The following solution is fast and works 0.075 seconds for the 20000 Fibonacci number (which has 4180 digits).</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">def</span> <span class="nf">accFib</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">Nm2</span><span class="o">=</span><span class="mi">0</span><span class="p">,</span> <span class="n">Nm1</span><span class="o">=</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">Nm2</span><span class="p">,</span> <span class="n">Nm1</span> <span class="o">=</span> <span class="n">Nm1</span><span class="p">,</span> <span class="n">Nm1</span><span class="o">+</span><span class="n">Nm2</span> <span class="k">return</span> <span class="n">Nm2</span> <span class="k">return</span> <span class="n">accFib</span><span class="p">(</span><span class="n">n</span><span class="p">)</span></code></pre></div> <h2>Additional ressources</h2> <p>The article on <a href="http://en.literateprograms.org/Fibonacci_numbers_(Python)">literate programs</a> is worth reading. They show some very different programs that calculate Fibonacci numbers.</p> Programmierparadigmen Klausur //martin-thoma.com/programmierparadigmen-klausur/ Thu, 24 Oct 2013 12:46:16 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/programmierparadigmen-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Programmierparadigmen&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn Prof. Dr. Snelting im Wintersemester 2013/2014 gehört.</div> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <h3 id="vorlesung">Vorlesung</h3> <table> <tr> <th>Datum</th> <th>Kapitel</th> <th>Inhalt</th> </tr> <tr> <td>23.10.2013</td> <td>Funktionale Programmierung <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/intern/10_FunktionaleProgrammierung.pdf">10</a></td> <td>Haskell: Quicksort, Listen, <a href="http://learnyouahaskell.com/higher-order-functions#maps-and-filters">Filter</a>, <a href="http://www.haskell.org/haskellwiki/Syntactic_sugar/Cons">Cons-Operator</a></td> </tr> <tr> <td>25.10.2013</td> <td>Funktionale Programmierung <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/intern/11_FunktionaleProgrammierung.pdf">11</a></td> <td>Haskell: filter, map, iter, foldr, foldl, Currying, Extensionalitätsprinzip, Kombinatoren (Summe, Produkt), flatten, cons, zip</td> </tr> <tr> <td>30.10.2013</td> <td>Funktionale Programmierung <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/intern/12_FunktionaleProgrammierung.pdf">12</a></td> <td>Haskell: zipWith, short circuit evaluation, foldl, foldr, Unendliche Listen, Typen, Polymorphie</td> </tr> <tr> <td>06.11.2013</td> <td></td> <td>Backtracking, Algebraische und rekursive Datentypen, map for trees, Typklassen</td> </tr> <tr> <td>08.11.2013</td> <td>&nbsp;</td> <td>Typklassen, Monaden</td> </tr> <tr> <td>13.11.2013</td> <td>&nbsp;</td> <td>Sichtbarkeitsbereich `$\subseteq$` Gültigkeitsbereich; `$\alpha$` / `$\eta$`-Äqivalenz, Redex; Funktion, die sich als eigenes Argument nimmt; `$\lambda$`-Klakül ist Turing-Mächtig</td> </tr> <tr> <td>29.11.2013</td> <td>Logische Programmierung</td> <td>Prolog</td> </tr> <tr> <td>10.01.2014</td> <td>Scala</td> <td>Kein `;`, weniger verbose als Java, ...</td> </tr> <tr> <td>15.01.2014</td> <td>Scala</td> <td>Concurrency in Scala: Actors, react; MPI, OpenMP</td> </tr> <tr> <td>22.01.2014</td> <td>-</td> <td>X10: async, val, var</td> </tr> <tr> <td>24.01.2014</td> <td>-</td> <td>C (<abbr title="Immer aus Hauptspeicher, nie aus Cache holen">volatile</abbr>)</td> </tr> </table> <h3 id="bungsbltter">Übungsblätter</h3> <table> <tr> <th>Übungsblatt</th> <th>Inhalt</th> </tr> <tr> <td><a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/uebung/blaetter/blatt0.pdf" rel="nofollow">ÜB 0</a>: Haskell</td> <td>Haskell installieren (siehe <a href="http://wiki.ubuntuusers.de/Haskell">UbuntuUsers</a>), Maximum dreier Zahlen berechnen</td> </tr> <tr> <td><a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/uebung/blaetter/blatt1.pdf" rel="nofollow">ÜB 1</a>: Rekursive Funktionen in Haskell</td> <td>Potenzen, Primzahlen, Sortieren</td> </tr> </table> <h3 id="tutorium">Tutorium</h3> <h4 id="section">16.12.2013</h4> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>let f = \ x.plus x x in f (f c_2) ^= (\ f. f (f c_2)) (\x. plus x x) </pre></div> </div> </div> <p><code>let</code> wird wegen dem Typsystem benötigt (<code>let</code> ist polymorph, <code>$\lambda$</code>-Term nicht).</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>let f = \x.1 in (f 7) + (f[&quot;a&quot;]) ^= (\ f. ) (\ x. 1) f: \alpha_5 -&gt; int f: \forall \alpha_5. \alpha_5 \rightarrow int </pre></div> </div> </div> <h2 id="material">Material</h2> <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/blob/master/documents/Programmierparadigmen/Programmierparadigmen.pdf?raw=true">Inoffizielles Skript</a> in A5 (<a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/Programmierparadigmen">LaTeX-Quellen</a>): Wer das gerne für ca. 10 Euro in SW gedruckt mit Ringbindung hätte, soll mir eine E-Mail schreiben</li> <li><a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/">Vorlesungswebsite</a> und <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/uebung/#unterlagen">Übungsblätter</a></li> <li>Ein <a href="https://ankiweb.net/shared/info/3121773115">Anki-Deck</a> (NICHT meines!)</li> <li>Stackexchange: <ul> <li><a href="http://math.stackexchange.com/q/704401/6876">What is the meaning of M ⊨ φ?</a></li> <li><a href="http://stackoverflow.com/q/22283936/562769">How can I compile the x10 example?</a></li> <li><a href="http://stackoverflow.com/q/22643004/562769">What is the difference of ‘async’ before or after ‘for’ in X10?</a></li> <li><a href="http://stackoverflow.com/q/22709063/562769">How do I generate and print Fibonacci numbers in X10?</a></li> <li><a href="http://stackoverflow.com/q/22731293/562769">What is the difference between ifne and ifnonnull?</a></li> <li><a href="http://stackoverflow.com/q/22594719/562769">Haskell list comprehension - list of all list splits</a></li> <li><a href="http://stackoverflow.com/q/22177931/562769">How can I ask questions on a family tree in Prolog?</a></li> </ul> </li> </ul> <h2 id="klausurvorbereitung">Klausurvorbereitung</h2> <ul> <li><a href="http://www.haskell.org/haskellwiki/H-99:_Ninety-Nine_Haskell_Problems">H-99: Ninety-Nine Haskell Problems</a></li> <li><a href="https://sites.google.com/site/prologsite/prolog-problems">P-99: Ninety-Nine Prolog Problems</a></li> <li>Scala <ul> <li><a href="http://aperiodic.net/phil/scala/s-99/">S-99: Ninety-Nine Scala Problems</a></li> <li><a href="http://joelabrahamsson.com/learning-scala/">Learning Scala</a> by Joel Abrahamsson</li> </ul> </li> </ul> <h2 id="bungsbetrieb">Übungsbetrieb</h2> <ul> <li>Wo sind die Übungsblätter: <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/uebung/#unterlagen">Link</a></li> <li>Abgabeform: auf Papier und via E-Mail</li> <li>Abgabe: Datum steht auf den Übungsblättern; Ort: Kasten im Keller des Infobaus</li> <li>Rücknahme: im Tutorium</li> <li>Turnus: wöchentlich, erscheint am Donnerstag.</li> <li>Übungsschein verpflichtend: Es gibt keinen Übungsschein.</li> <li>Bonus durch Übungsschein: Es gibt keinen Klausurbonus.</li> </ul> <h2 id="termine-und-klausurablauf">Termine und Klausurablauf</h2> <p>Siehe <a href="http://www.informatik.kit.edu/klausuren.php">Klausurtermine-Seite</a> für zukünftige Termine (z.B. <a href="http://www.informatik.kit.edu/klausuren.php?kid=504.35">Programmierparadigmen am 23.09.2014</a>)</p> <p><strong>Datum</strong>: Donnerstag, den 10. April 2014 von 14:00 bis 16:00 Uhr (<a href="https://pp.info.uni-karlsruhe.de/lehre/WS201314/paradigmen/">Quelle</a>)<br /> <strong>Ort</strong>: Audimax (<a href="https://pp.info.uni-karlsruhe.de/lehre/WS201314/paradigmen/#klausuren">Quelle</a>)<br /> <strong>Punkte</strong>: 120<br /> <strong>Punkteverteilung</strong>: Vermutlich etwas in dieser Richtung:</p> <ul> <li>25 Punkte: Haskell / Scala</li> <li>20 Punkte: Logische Programmierung</li> <li>25 Punkte: Typinferenz / Lambda-Kalkül</li> <li>10 Punkte: C</li> <li>10 Punkte: MPI</li> <li>10 Punkte: X10</li> <li>20 Punkte: Compilerbau</li> </ul> <p><strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: Gibt es nicht.<br /> <strong>Bonuspunkte</strong>: Gibt es nicht.<br /> <strong>Ergebnisse</strong>: stehen seit dem 17.04.2014 fest<br /> <strong>Einsicht</strong>: am Mittwoch den 30.04.2014, 14:00 Uhr - 16:00 in Raum 010, Informatik Gebäude (Geb. 50.34) (bekanntgegeben über <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/index.php">Vorlesungswebsite</a> am 17.04.2014)<br /> <strong>Erlaubte Hilfsmittel</strong>: (siehe <a href="http://pp.ipd.kit.edu/lehre/WS201314/paradigmen/">Website</a>)</p> <blockquote>Erlaubte Hilfsmittel für die Klausur sind alle Quellen in Papierform, insbesondere <ul> <li>Vorlesungsfolien der Veranstaltung Programmierparadigmen</li> <li>Übungszettel und Beispiellösungen der Veranstaltung Programmierparadigmen</li> <li>Bücher, Ausdrucke und beliebige eigenen Aufzeichnungen</li> </ul> </blockquote> <h2 id="ergebnisse">Ergebnisse</h2> <p>Stehen seit dem 17.04.2014 fest.</p> <h2 id="kritik">Kritik</h2> <p>In der Vorlesung werden zu viele Inhalte behandelt. Eine Folge ist, dass nichts richtig behandelt werden. Außerdem erscheinen mir einige der Inhalte weder in der Wissenschaft noch in der Wirtschaft relevant zu sein (Prolog, X10). Ich würde vorschlagen diese Inhalte zu entfernen. Wenn man der Meinung ist, dass man Parallelität mehr behandeln sollte, dann wäre vermutlich CUDA deutlich wichtiger als X10.</p> Working with Terminal //martin-thoma.com/working-terminal/ Tue, 22 Oct 2013 10:40:46 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/working-terminal <p>I’ve just switched from <a href="https://en.wikipedia.org/wiki/Bash_(Unix_shell)">Bash</a> to <a href="https://en.wikipedia.org/wiki/Z_shell">ZSH</a> because of <a href="https://github.com/robbyrussell/oh-my-zsh">oh-my-ZSH</a>. I think this is just the right time to explain the words Shell, command line, Terminal, Bash and ZSH.</p> <p><a href="https://en.wikipedia.org/wiki/GNOME_Terminal">Terminal</a> is an terminal emulator, sometimes also called a “terminal window”. I work in a window environment (MATE) and I want to use command line tools within that environment. So I need a “terminal window”:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/10/teriminal-window.png"><img src="//martin-thoma.com/captions/teriminal-window.png" alt="Terminal Window with ZSH and Bash" width="299" height="168" class="size-medium" /></a><p class="wp-caption-text">Terminal Window with ZSH and Bash</p></div> <p>ZSH and Bash are both Unix shells. A shell is a command line interpreter that provides a text-based user interface.</p> <p>Command line describes the textual way you interact with the computer. When you’re in a graphical user interface situation you interact by manipulating windows with your keyboard/mouse. When you’re in a text-based user interface situation, you interact by entering commands in a line (hence command line).</p> <h2 id="solarized-dark-theme">Solarized Dark Theme</h2> <p>The <a href="http://ethanschoonover.com/solarized">Solarized Dark Theme</a> is very good for command line. It can be installed like this as explained <a href="https://github.com/oz123/solarized-mate-terminal">here</a>:</p> <pre><code>git clone https://github.com/oz123/solarized-mate-terminal.git cd solarized-mate-terminal ./solarized-mate.sh dark </code></pre> <p>restart the terminal.</p> <h2 id="oh-my-zsh-installation">Oh-my-ZSH Installation</h2> <p>Oh-my-ZSH is a plugin for ZSH. I think this plugin is very good and makes a big difference to Bash. So when you look at the screenshots below, keep in mind that this is not a “plain vanilla” zsh.</p> <ul> <li>Install “<a href="https://github.com/robbyrussell/oh-my-zsh">Oh-my-ZSH</a>”</li> <li>Install “<a href="https://github.com/Lokaltog/powerline-fonts">powerline fonts</a>” and change your Terminal font to one of them</li> <li>Change your Terminal theme to “agnoster” by setting <code>ZSH_THEME="agnoster"</code> in <strong>~/.zshrc</strong></li> <li>Set your terminal theme to “Solarized Dark” (<a href="http://www.mintmate.org/?p=13">description</a>)</li> <li>Make ZSH your default Shell in MATE Terminal (<a href="http://askubuntu.com/a/342342/10425">description</a>) and eventually <code>sudo chsh -s /usr/bin/zsh username</code></li> </ul> <h2 id="zsh-and-bash">ZSH and Bash</h2> <p>Here are some differences. On the left side is zsh, on the right is bash:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/10/bash-vs-zsh-cd.png" class="image"><img src="//martin-thoma.com/captions/bash-vs-zsh-cd.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Bash vs zsh: cd command completion</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/10/bash-vs-zsh-git.png" class="image"><img src="//martin-thoma.com/captions/bash-vs-zsh-git.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Bash vs zsh: Git prompt indicator</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/10/bash-vs-zsh-spelling-correction.png" class="image"><img src="//martin-thoma.com/captions/bash-vs-zsh-spelling-correction.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Bash vs zsh: Spelling correction</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/10/bash-vs-zsh-time.png" class="image"><img src="//martin-thoma.com/captions/bash-vs-zsh-time.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Bash vs zsh: time command</div></div></li></ul> <p>I like the time command of bash more, but that’s it. All other interactions are either almost the same or better in zsh. I especially like that zsh doesn’t print everything again when you autocomplete with tab. And it also autocompletes when you make an capitalization error.</p> <p>I also begin to like the Git-specific prompt indicators:</p> <div style="width: 246px" class="wp-caption aligncenter"><a href="../images/2013/10/oh-my-zsh-git-added.png"><img src="../images/2013/10/oh-my-zsh-git-added.png" alt="ZSH 'git add' indicator" width="" height="" class="size-full" /></a><p class="wp-caption-text">ZSH 'git add' indicator</p></div> <h2 id="some-usefull-tools">Some usefull tools</h2> <h3 id="ack">ack</h3> <p>You might already know <code>grep</code>. And if you’ve worked with it, you might already have typed something like the following:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>grep --exclude-dir=&quot;.svn&quot; &quot;searchterm&quot; * grep -rI &quot;onlytextSearchterm&quot; . </pre></div> </div> </div> <p>An alternative to <code>grep</code> is <code>ack</code> (for Ubuntu users: <code>ack-grep</code>). See <a href="http://beyondgrep.com/">beyondgrep.com</a>.</p> <h2 id="windows">Windows</h2> <p>It seems to be possible to get something similar (the same?) for Windows. See <a href="https://github.com/haithembelhaj/oh-my-cygwin/blob/master/README.md">OH MY CYGWIN</a>.</p> Part III: Matrix multiplication on multiple cores in Python, Java and C++ //martin-thoma.com/part-iii-matrix-multiplication-on-multiple-cores-in-python-java-and-c/ Mon, 21 Oct 2013 16:39:35 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/part-iii-matrix-multiplication-on-multiple-cores-in-python-java-and-c <div class="info">This is Part III of my matrix multiplication series. <a href="../matrix-multiplication-python-java-cpp/">Part I</a> was about simple matrix multiplication algorithms and <a href="../strassen-algorithm-in-python-java-cpp/">Part II</a> was about the Strassen algorithm. <a href="../part-iii-matrix-multiplication-on-multiple-cores-in-python-java-and-c/">Part III</a> is about parallel matrix multiplication.</div> <p>We got some pretty interesting results for matrix multiplication so far. Now, I would like to get to know in how far performance increases (or decreases) if I make use of multiple cores. I only have two cores, so I hope somebody with a better computer will also run the ikj single core algorithm form part I and the parallel version from this article and post the results as a comment.</p> <h2>The implementations</h2> <p>As last time, I’ve added the scripts to a <a href="https://github.com/MartinThoma/matrix-multiplication">GIT repository</a>. So you can test it on your machine.</p> <p>Before we start implementing code for multiple processors, we have to get an algorithm that is actually parallelisable. You could use <a href="https://en.wikipedia.org/wiki/Cannon%27s_algorithm">Cannon’s algorithm</a>, a algorithm that makes use of <a href="http://en.wikipedia.org/wiki/Systolic_array">systolic arrays</a> or try to find a solution by your own. The <a href="http://www.netlib.org/lapack/lawnspdf/lawn96.pdf">Scalable Universal Matrix Multiplication Algorithm</a> (short: SUMMA) could also work. The paper that I’ve linked is well-written and easy to understand. You should definitively read it, if you’re interested in matrix multiplication.</p> <p>I will not use any advanced algorithm in this article. I will make the outer most for loop of the ikj-algorithm (see part I) execute in parallel.</p> <p>More about parallel matrix multiplication:</p> <ul> <li><a href="http://www.mcs.anl.gov/~itf/dbpp/text/node45.html">Case Study: Matrix Multiplication</a></li> <li><a href="http://berrendorf.inf.fh-bonn-rhein-sieg.de/Parallel/index.html">berrendorf</a></li> <li><a href="http://en.wikipedia.org/wiki/Matrix_multiplication#Algorithms_for_efficient_matrix_multiplication">Algorithms for efficient matrix multiplication</a></li> <li><a href="http://en.wikipedia.org/wiki/Coppersmith%E2%80%93Winograd_algorithm">Coppersmith-Winograd algorith</a></li> </ul> <h2>Python</h2> <p>Because of global interpreter lock (GIL), you need to start new processes in Python (<a href="http://stackoverflow.com/a/9786225/562769">source</a>).</p> <p>The ikj single core algorithm implemented in Python needs:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>python ikjMultiplication.py -i 2000.in &gt; 2000-nonparallel.out real 36m0.699s user 35m53.463s sys 0m2.356s</code></pre></div> <p>The most simple way to parallelize the ikj algorith is to use the <a href="http://docs.python.org/2/library/multiprocessing.html">multiprocessing module</a> and compute every line of the result matrix C with a new process. But for the 2000x2000-example, this would mean we started 2000 processes. The overhead is much worse than the benefit:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>python ikjMultiplication.py -i 2000.in &gt; 2000-parallel.out real 20m47.693s user 40m34.460s sys 0m2.092s</code></pre></div> <p>When we share memory, the code looks like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">multiprocessing</span><span class="o">,</span> <span class="nn">numpy</span><span class="o">,</span> <span class="nn">ctypes</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">A</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="k">if</span> <span class="n">line</span> <span class="o">!=</span> <span class="s">&quot;&quot;</span><span class="p">:</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">else</span><span class="p">:</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">,</span> <span class="n">f</span><span class="p">):</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">)</span> <span class="k">def</span> <span class="nf">lineMult</span><span class="p">(</span><span class="n">start</span><span class="p">):</span> <span class="k">global</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">mp_arr</span><span class="p">,</span> <span class="n">part</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="c"># create a new numpy array using the same memory as mp_arr</span> <span class="n">arr</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">frombuffer</span><span class="p">(</span><span class="n">mp_arr</span><span class="o">.</span><span class="n">get_obj</span><span class="p">(),</span> <span class="n">dtype</span><span class="o">=</span><span class="n">ctypes</span><span class="o">.</span><span class="n">c_int</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">arr</span><span class="o">.</span><span class="n">reshape</span><span class="p">((</span><span class="n">n</span><span class="p">,</span><span class="n">n</span><span class="p">))</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">start</span><span class="p">,</span> <span class="n">start</span><span class="o">+</span><span class="n">part</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">def</span> <span class="nf">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">threadNumber</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">pool</span> <span class="o">=</span> <span class="n">multiprocessing</span><span class="o">.</span><span class="n">Pool</span><span class="p">(</span><span class="n">threadNumber</span><span class="p">)</span> <span class="n">pool</span><span class="o">.</span><span class="n">map</span><span class="p">(</span><span class="n">lineMult</span><span class="p">,</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="n">n</span><span class="p">,</span> <span class="n">part</span><span class="p">))</span> <span class="c"># mp_arr and arr share the same memory</span> <span class="n">arr</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">frombuffer</span><span class="p">(</span><span class="n">mp_arr</span><span class="o">.</span><span class="n">get_obj</span><span class="p">(),</span> <span class="n">dtype</span><span class="o">=</span><span class="n">ctypes</span><span class="o">.</span><span class="n">c_int</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">arr</span><span class="o">.</span><span class="n">reshape</span><span class="p">((</span><span class="n">n</span><span class="p">,</span><span class="n">n</span><span class="p">))</span> <span class="k">return</span> <span class="n">C</span> <span class="k">def</span> <span class="nf">extant_file</span><span class="p">(</span><span class="n">x</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;</span> <span class="sd"> &#39;Type&#39; for argparse - checks that file exists but does not open.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">isfile</span><span class="p">(</span><span class="n">x</span><span class="p">):</span> <span class="k">raise</span> <span class="n">argparse</span><span class="o">.</span><span class="n">ArgumentError</span><span class="p">(</span><span class="s">&quot;{0} does not exist&quot;</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">x</span><span class="p">))</span> <span class="k">return</span> <span class="n">x</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">argparse</span><span class="o">,</span> <span class="nn">sys</span> <span class="kn">from</span> <span class="nn">os.path</span> <span class="kn">import</span> <span class="n">isfile</span> <span class="kn">from</span> <span class="nn">argparse</span> <span class="kn">import</span> <span class="n">ArgumentParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">ArgumentParser</span><span class="p">(</span><span class="n">description</span><span class="o">=</span><span class="s">&quot;ikjMatrix multiplication&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="s">&quot;--input&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">required</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="n">extant_file</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-o&quot;</span><span class="p">,</span> <span class="s">&quot;--output&quot;</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="n">argparse</span><span class="o">.</span><span class="n">FileType</span><span class="p">(</span><span class="n">mode</span><span class="o">=</span><span class="s">&#39;w&#39;</span><span class="p">),</span> <span class="n">default</span><span class="o">=</span><span class="n">sys</span><span class="o">.</span><span class="n">stdout</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;output&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;file to write output to (default=stdout)&quot;</span><span class="p">)</span> <span class="n">args</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">n</span><span class="p">,</span> <span class="n">m</span><span class="p">,</span> <span class="n">p</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">),</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="mi">0</span><span class="p">]),</span> <span class="nb">len</span><span class="p">(</span><span class="n">B</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="n">threadNumber</span> <span class="o">=</span> <span class="mi">2</span> <span class="n">part</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="o">/</span> <span class="n">threadNumber</span> <span class="k">if</span> <span class="n">part</span> <span class="o">&lt;</span> <span class="mi">1</span><span class="p">:</span> <span class="n">part</span> <span class="o">=</span> <span class="mi">1</span> <span class="c"># shared, can be used from multiple processes</span> <span class="n">mp_arr</span> <span class="o">=</span> <span class="n">multiprocessing</span><span class="o">.</span><span class="n">Array</span><span class="p">(</span><span class="n">ctypes</span><span class="o">.</span><span class="n">c_int</span><span class="p">,</span> <span class="n">n</span><span class="o">*</span><span class="n">p</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">threadNumber</span><span class="p">)</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">,</span> <span class="n">args</span><span class="o">.</span><span class="n">output</span><span class="p">)</span></code></pre></div> <p>and it needs MUCH more time:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>python ikjMultiplication-shared.py -i 2000.in &gt; 2000-parallel-2threads.out real 131m35.433s user 250m36.820s sys 0m9.533s</code></pre></div> <p>When we don’t use shared memory, things run faster:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">multiprocessing</span><span class="o">,</span> <span class="nn">numpy</span><span class="o">,</span> <span class="nn">ctypes</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">A</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="k">if</span> <span class="n">line</span> <span class="o">!=</span> <span class="s">&quot;&quot;</span><span class="p">:</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">else</span><span class="p">:</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">,</span> <span class="n">f</span><span class="p">):</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">)</span> <span class="k">def</span> <span class="nf">lineMult</span><span class="p">(</span><span class="n">start</span><span class="p">):</span> <span class="k">global</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">C</span><span class="p">,</span> <span class="n">part</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">start</span><span class="p">,</span> <span class="n">start</span><span class="o">+</span><span class="n">part</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">def</span> <span class="nf">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">threadNumber</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">pool</span> <span class="o">=</span> <span class="n">multiprocessing</span><span class="o">.</span><span class="n">Pool</span><span class="p">(</span><span class="n">threadNumber</span><span class="p">)</span> <span class="n">pool</span><span class="o">.</span><span class="n">map</span><span class="p">(</span><span class="n">lineMult</span><span class="p">,</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="n">n</span><span class="p">,</span> <span class="n">part</span><span class="p">))</span> <span class="k">return</span> <span class="n">C</span> <span class="k">def</span> <span class="nf">extant_file</span><span class="p">(</span><span class="n">x</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;</span> <span class="sd"> &#39;Type&#39; for argparse - checks that file exists but does not open.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">isfile</span><span class="p">(</span><span class="n">x</span><span class="p">):</span> <span class="k">raise</span> <span class="n">argparse</span><span class="o">.</span><span class="n">ArgumentError</span><span class="p">(</span><span class="s">&quot;{0} does not exist&quot;</span><span class="o">.</span><span class="n">format</span><span class="p">(</span><span class="n">x</span><span class="p">))</span> <span class="k">return</span> <span class="n">x</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">argparse</span><span class="o">,</span> <span class="nn">sys</span> <span class="kn">from</span> <span class="nn">os.path</span> <span class="kn">import</span> <span class="n">isfile</span> <span class="kn">from</span> <span class="nn">argparse</span> <span class="kn">import</span> <span class="n">ArgumentParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">ArgumentParser</span><span class="p">(</span><span class="n">description</span><span class="o">=</span><span class="s">&quot;ikjMatrix multiplication&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="s">&quot;--input&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">required</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="n">extant_file</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-o&quot;</span><span class="p">,</span> <span class="s">&quot;--output&quot;</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="n">argparse</span><span class="o">.</span><span class="n">FileType</span><span class="p">(</span><span class="n">mode</span><span class="o">=</span><span class="s">&#39;w&#39;</span><span class="p">),</span> <span class="n">default</span><span class="o">=</span><span class="n">sys</span><span class="o">.</span><span class="n">stdout</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;output&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;file to write output to (default=stdout)&quot;</span><span class="p">)</span> <span class="n">args</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">n</span><span class="p">,</span> <span class="n">m</span><span class="p">,</span> <span class="n">p</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">),</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="mi">0</span><span class="p">]),</span> <span class="nb">len</span><span class="p">(</span><span class="n">B</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="n">threadNumber</span> <span class="o">=</span> <span class="mi">2</span> <span class="n">part</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="o">/</span> <span class="n">threadNumber</span> <span class="k">if</span> <span class="n">part</span> <span class="o">&lt;</span> <span class="mi">1</span><span class="p">:</span> <span class="n">part</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="n">C</span> <span class="o">=</span> <span class="n">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">threadNumber</span><span class="p">)</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">,</span> <span class="n">args</span><span class="o">.</span><span class="n">output</span><span class="p">)</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>python ikjMultiplication.py -i 2000.in &gt; 2000-parallel-4threads.out real 22m46.066s user 41m42.396s sys 0m2.324s</code></pre></div> <h2>Java</h2> <p>Shell.java:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.io.BufferedReader</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.FileReader</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.IOException</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.LinkedList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.concurrent.Callable</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.concurrent.ExecutionException</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.concurrent.ExecutorService</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.concurrent.Executors</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.concurrent.Future</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Shell</span> <span class="o">{</span> <span class="kd">static</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="nf">read</span><span class="o">(</span><span class="n">String</span> <span class="n">filename</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;();</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;();</span> <span class="n">String</span> <span class="n">thisLine</span><span class="o">;</span> <span class="k">try</span> <span class="o">{</span> <span class="n">BufferedReader</span> <span class="n">br</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">BufferedReader</span><span class="o">(</span><span class="k">new</span> <span class="nf">FileReader</span><span class="o">(</span><span class="n">filename</span><span class="o">));</span> <span class="c1">// Begin reading A</span> <span class="k">while</span> <span class="o">((</span><span class="n">thisLine</span> <span class="o">=</span> <span class="n">br</span><span class="o">.</span><span class="na">readLine</span><span class="o">())</span> <span class="o">!=</span> <span class="kc">null</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">thisLine</span><span class="o">.</span><span class="na">trim</span><span class="o">().</span><span class="na">equals</span><span class="o">(</span><span class="s">&quot;&quot;</span><span class="o">))</span> <span class="o">{</span> <span class="k">break</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">line</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">String</span><span class="o">[]</span> <span class="n">lineArray</span> <span class="o">=</span> <span class="n">thisLine</span><span class="o">.</span><span class="na">split</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">String</span> <span class="n">number</span> <span class="o">:</span> <span class="n">lineArray</span><span class="o">)</span> <span class="o">{</span> <span class="n">line</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">number</span><span class="o">));</span> <span class="o">}</span> <span class="n">A</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">line</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="c1">// Begin reading B</span> <span class="k">while</span> <span class="o">((</span><span class="n">thisLine</span> <span class="o">=</span> <span class="n">br</span><span class="o">.</span><span class="na">readLine</span><span class="o">())</span> <span class="o">!=</span> <span class="kc">null</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">line</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">String</span><span class="o">[]</span> <span class="n">lineArray</span> <span class="o">=</span> <span class="n">thisLine</span><span class="o">.</span><span class="na">split</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">String</span> <span class="n">number</span> <span class="o">:</span> <span class="n">lineArray</span><span class="o">)</span> <span class="o">{</span> <span class="n">line</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">number</span><span class="o">));</span> <span class="o">}</span> <span class="n">B</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">line</span><span class="o">);</span> <span class="o">}</span> <span class="n">br</span><span class="o">.</span><span class="na">close</span><span class="o">();</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">IOException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Error: &quot;</span> <span class="o">+</span> <span class="n">e</span><span class="o">);</span> <span class="o">}</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="n">res</span> <span class="o">=</span> <span class="k">new</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;();</span> <span class="n">res</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">A</span><span class="o">);</span> <span class="n">res</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">B</span><span class="o">);</span> <span class="k">return</span> <span class="n">res</span><span class="o">;</span> <span class="o">}</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">printMatrix</span><span class="o">(</span><span class="kt">int</span><span class="o">[][]</span> <span class="n">matrix</span><span class="o">)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span><span class="o">[]</span> <span class="n">line</span> <span class="o">:</span> <span class="n">matrix</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">StringBuilder</span> <span class="n">sb</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">StringBuilder</span><span class="o">(</span><span class="n">matrix</span><span class="o">.</span><span class="na">length</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">number</span> <span class="o">:</span> <span class="n">line</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">i</span> <span class="o">!=</span> <span class="mi">0</span><span class="o">)</span> <span class="o">{</span> <span class="n">sb</span><span class="o">.</span><span class="na">append</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">i</span><span class="o">++;</span> <span class="o">}</span> <span class="n">sb</span><span class="o">.</span><span class="na">append</span><span class="o">(</span><span class="n">number</span><span class="o">);</span> <span class="o">}</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">sb</span><span class="o">.</span><span class="na">toString</span><span class="o">());</span> <span class="o">}</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">parallelMult</span><span class="o">(</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span><span class="o">,</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span><span class="o">,</span> <span class="kt">int</span> <span class="n">threadNumber</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">()][</span><span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">).</span><span class="na">size</span><span class="o">()];</span> <span class="n">ExecutorService</span> <span class="n">executor</span> <span class="o">=</span> <span class="n">Executors</span><span class="o">.</span><span class="na">newFixedThreadPool</span><span class="o">(</span><span class="n">threadNumber</span><span class="o">);</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">Future</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">[][]&gt;&gt;</span> <span class="n">list</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Future</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">[][]&gt;&gt;();</span> <span class="kt">int</span> <span class="n">part</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">()</span> <span class="o">/</span> <span class="n">threadNumber</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">part</span> <span class="o">&lt;</span> <span class="mi">1</span><span class="o">)</span> <span class="o">{</span> <span class="n">part</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="o">}</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">();</span> <span class="n">i</span> <span class="o">+=</span> <span class="n">part</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">i</span><span class="o">);</span> <span class="n">Callable</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">[][]&gt;</span> <span class="n">worker</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">LineMultiplier</span><span class="o">(</span><span class="n">A</span><span class="o">,</span> <span class="n">B</span><span class="o">,</span> <span class="n">i</span><span class="o">,</span> <span class="n">i</span><span class="o">+</span><span class="n">part</span><span class="o">);</span> <span class="n">Future</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">[][]&gt;</span> <span class="n">submit</span> <span class="o">=</span> <span class="n">executor</span><span class="o">.</span><span class="na">submit</span><span class="o">(</span><span class="n">worker</span><span class="o">);</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">submit</span><span class="o">);</span> <span class="o">}</span> <span class="c1">// now retrieve the result</span> <span class="kt">int</span> <span class="n">start</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="kt">int</span> <span class="n">CF</span><span class="o">[][];</span> <span class="k">for</span> <span class="o">(</span><span class="n">Future</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">[][]&gt;</span> <span class="n">future</span> <span class="o">:</span> <span class="n">list</span><span class="o">)</span> <span class="o">{</span> <span class="k">try</span> <span class="o">{</span> <span class="n">CF</span> <span class="o">=</span> <span class="n">future</span><span class="o">.</span><span class="na">get</span><span class="o">();</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="n">start</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">start</span><span class="o">+</span><span class="n">part</span><span class="o">;</span> <span class="n">i</span> <span class="o">+=</span> <span class="mi">1</span><span class="o">)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">]</span> <span class="o">=</span> <span class="n">CF</span><span class="o">[</span><span class="n">i</span><span class="o">];</span> <span class="o">}</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">InterruptedException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">e</span><span class="o">.</span><span class="na">printStackTrace</span><span class="o">();</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">ExecutionException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">e</span><span class="o">.</span><span class="na">printStackTrace</span><span class="o">();</span> <span class="o">}</span> <span class="n">start</span><span class="o">+=</span><span class="n">part</span><span class="o">;</span> <span class="o">}</span> <span class="n">executor</span><span class="o">.</span><span class="na">shutdown</span><span class="o">();</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">String</span> <span class="n">filename</span><span class="o">;</span> <span class="kt">int</span> <span class="n">cores</span> <span class="o">=</span> <span class="n">Runtime</span><span class="o">.</span><span class="na">getRuntime</span><span class="o">().</span><span class="na">availableProcessors</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Number of cores:\t&quot;</span> <span class="o">+</span> <span class="n">cores</span><span class="o">);</span> <span class="kt">int</span> <span class="n">threads</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">args</span><span class="o">.</span><span class="na">length</span> <span class="o">&lt;</span> <span class="mi">3</span><span class="o">)</span> <span class="o">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;3.in&quot;</span><span class="o">;</span> <span class="n">threads</span> <span class="o">=</span> <span class="n">cores</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">args</span><span class="o">[</span><span class="mi">1</span><span class="o">];</span> <span class="n">threads</span> <span class="o">=</span> <span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">args</span><span class="o">[</span><span class="mi">2</span><span class="o">]);</span> <span class="o">}</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="n">matrices</span> <span class="o">=</span> <span class="n">read</span><span class="o">(</span><span class="n">filename</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="n">parallelMult</span><span class="o">(</span><span class="n">A</span><span class="o">,</span> <span class="n">B</span><span class="o">,</span> <span class="n">threads</span><span class="o">);</span> <span class="n">printMatrix</span><span class="o">(</span><span class="n">C</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>LineMultiplier.java:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.concurrent.Callable</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">LineMultiplier</span> <span class="kd">implements</span> <span class="n">Callable</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">[][]&gt;</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span><span class="o">;</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span><span class="o">;</span> <span class="kt">int</span> <span class="n">start</span><span class="o">;</span> <span class="kt">int</span> <span class="n">end</span><span class="o">;</span> <span class="kd">public</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span><span class="o">;</span> <span class="kd">public</span> <span class="nf">LineMultiplier</span><span class="o">(</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">a</span><span class="o">,</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">b</span><span class="o">,</span> <span class="kt">int</span> <span class="n">s</span><span class="o">,</span> <span class="kt">int</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">A</span> <span class="o">=</span> <span class="n">a</span><span class="o">;</span> <span class="n">B</span> <span class="o">=</span> <span class="n">b</span><span class="o">;</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">a</span><span class="o">.</span><span class="na">size</span><span class="o">()][</span><span class="n">b</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">).</span><span class="na">size</span><span class="o">()];</span> <span class="n">start</span> <span class="o">=</span> <span class="n">s</span><span class="o">;</span> <span class="n">end</span> <span class="o">=</span> <span class="n">e</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">call</span><span class="o">()</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="n">start</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">end</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">B</span><span class="o">.</span><span class="na">size</span><span class="o">();</span> <span class="n">k</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">).</span><span class="na">size</span><span class="o">();</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">+=</span> <span class="n">A</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">k</span><span class="o">)</span> <span class="o">*</span> <span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">k</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Execute it with only one thread:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>java Shell -i 2000.in <span class="m">1</span> &gt; 2000-paralllel.out Number of cores: 2 0 real 0m40.571s user 0m42.259s sys 0m0.388s</code></pre></div> <p>Execute it with two threads:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>java Shell -i 2000.in <span class="m">2</span> &gt; 2000-paralllel.out Number of cores: 2 0 1000 real 0m30.188s user 0m54.999s sys 0m0.512s</code></pre></div> <p>Note that real time is lower than user time. The reason is simply that the execution time on each processor is added. So user time might be double as high as real time!</p> <p>We got from 40.571s down to 0m30.188s!</p> <h3>Information for parallelism</h3> <ul> <li><a href="http://docs.oracle.com/javase/tutorial/essential/concurrency/pools.html">Thread pools</a></li> <li><a href="http://www.ibm.com/developerworks/library/j-jtp0730/index.html">Java theory and practice: Thread pools and work queues</a></li> <li><a href="http://stackoverflow.com/questions/tagged/java+parallel-processing">StackOverflow</a></li> </ul> <h2>C++</h2> <p>Making the ikj-algorithm parallel is trivial with C++. You only need to add <code>#pragma omp parallel for</code> before the outer most for loop and add <code>-fopenmp</code> as a compile flag! (If you really want to see the code, go to <a href="https://github.com/MartinThoma/matrix-multiplication/tree/master/C%2B%2B/Parallel">my Git repository</a>.)</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">$ </span><span class="nb">time</span> ./ikj-algorithm.out <span class="m">2</span> 2000.in &gt; 2000-parallel.out real 0m12.563s user 0m20.569s sys 0m0.156s</code></pre></div> <p>So we got from 20.407 seconds down to 12.563 seconds by adding only one line!</p> <h3>More Information</h3> <ul> <li><a href="http://bisqwit.iki.fi/story/howto/openmp/">Guide into OpenMP: Easy multithreading programming for C++</a></li> </ul> Part IV: How to multiply matrix with its transpose in Python and C++ //martin-thoma.com/part-iv-multiply-matrix-transpose-python-cpp/ Fri, 18 Oct 2013 17:41:13 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/part-iv-multiply-matrix-transpose-python-cpp <div class="info">This is Part IV of my matrix multiplication series. Part I was about simple implementations and libraries: <a href="../matrix-multiplication-python-java-cpp/">Performance of Matrix multiplication in Python, Java and C++</a>, Part II was about multiplication with the <a href="../strassen-algorithm-in-python-java-cpp/" title="Part II: The Strassen algorithm in Python, Java and C++">Strassen algorithm</a> and Part III will be about parallel matrix multiplication (I didn't write it yet).</div> <p>You can always multiply a matrix <code>$J \in \mathbb{R}^{n \times m}$</code> with its transpose <code>$J^T$</code>, because <code>$J^T \in \mathbb{R}^{m \times n}$</code>. You will get a matrix <code>$C \in \mathbb{R}^{n \times n}$</code>.</p> <p>Standard matrix multiplication of square matrices <code>$\in \mathbb{R}^{n \times n}$</code> is in <code>$\mathcal{O}(n^3)$</code>. With the Strassen algorithm you can multiply in <code>$\approx \cal O(n^{2.807})$</code>. But this is for general matrix multiplication. When we do <code>$J \cdot J^T$</code> we have more structure, so it might be possible to do this multiplication faster.</p> <p>One important property of the result matrix <code>$R = J \cdot J^T$</code> is symmetry. So <code>$R_{i,j} = R_{j,i}$</code>. If we used the ikj-algorithm for this multiplication, we needed <code>$n^2 \cdot m$</code> operations. This way, we only need <code>$\frac{n^2 +n}{2} \cdot m$</code> operations. Yes, I know, asymptotically it is irrelevant. But skipping almost half of the operations is still quite good.</p> <h2>Python</h2> <h3>NumPy</h3> <p>I guess doing this with NumPy is the best option:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">from</span> <span class="nn">optparse</span> <span class="kn">import</span> <span class="n">OptionParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">OptionParser</span><span class="p">()</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_option</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;2000.in&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="p">(</span><span class="n">options</span><span class="p">,</span> <span class="n">args</span><span class="p">)</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">J</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="n">J</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">return</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">J</span><span class="p">)</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">):</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">array</span><span class="p">(</span><span class="n">matrix</span><span class="p">)</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="n">J</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">options</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">R</span> <span class="o">=</span> <span class="n">J</span> <span class="o">*</span> <span class="n">J</span><span class="o">.</span><span class="n">T</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">R</span><span class="p">)</span></code></pre></div> <p>Time:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 7m19.223s user 7m12.147s sys 0m2.388s</code></pre></div> <p>When you want to do this in an application, you might want to use <a href="http://docs.scipy.org/doc/numpy/reference/generated/numpy.load.html">numpy.load</a>.</p> <h2>C++</h2> <h3>First try</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;sstream&gt;</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;fstream&gt;</span> <span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="cp">#include &lt;algorithm&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">getMatrixN</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">)</span> <span class="p">{</span> <span class="n">std</span><span class="o">::</span><span class="n">ifstream</span> <span class="n">inFile</span><span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">());</span> <span class="k">return</span> <span class="n">std</span><span class="o">::</span><span class="n">count</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">istreambuf_iterator</span><span class="o">&lt;</span><span class="kt">char</span><span class="o">&gt;</span><span class="p">(</span><span class="n">inFile</span><span class="p">),</span> <span class="n">std</span><span class="o">::</span><span class="n">istreambuf_iterator</span><span class="o">&lt;</span><span class="kt">char</span><span class="o">&gt;</span><span class="p">(),</span> <span class="sc">&#39;\n&#39;</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">getMatrixM</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">)</span> <span class="p">{</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="n">ifstream</span> <span class="n">infile</span><span class="p">;</span> <span class="n">infile</span><span class="p">.</span><span class="n">open</span> <span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">());</span> <span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">);</span> <span class="k">return</span> <span class="n">count</span><span class="p">(</span><span class="n">line</span><span class="p">.</span><span class="n">begin</span><span class="p">(),</span> <span class="n">line</span><span class="p">.</span><span class="n">end</span><span class="p">(),</span> <span class="sc">&#39;\t&#39;</span><span class="p">)</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">read</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">)</span> <span class="p">{</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="kt">FILE</span><span class="o">*</span> <span class="n">matrixfile</span> <span class="o">=</span> <span class="n">freopen</span><span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">(),</span> <span class="s">&quot;r&quot;</span><span class="p">,</span> <span class="n">stdin</span><span class="p">);</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">j</span><span class="p">;</span> <span class="kt">double</span> <span class="n">a</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">cin</span><span class="p">,</span> <span class="n">line</span><span class="p">)</span> <span class="o">&amp;&amp;</span> <span class="o">!</span><span class="n">line</span><span class="p">.</span><span class="n">empty</span><span class="p">())</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">a</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">fclose</span> <span class="p">(</span><span class="n">matrixfile</span><span class="p">);</span> <span class="p">}</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">ikjalgorithmTranspose</span><span class="p">(</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">J</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">T</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">R</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">,</span> <span class="kt">int</span> <span class="n">m</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">m</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="n">i</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">R</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">J</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">T</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">i</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">R</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">R</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">i</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="n">R</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="n">transpose</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">,</span> <span class="kt">int</span> <span class="n">m</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">m</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">B</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">matrix</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">j</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">matrix</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span> <span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="n">string</span> <span class="n">filename</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">&lt;</span> <span class="mi">3</span><span class="p">)</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;../Testing/5161x7058.in&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">argv</span><span class="p">[</span><span class="mi">2</span><span class="p">];</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">getMatrixN</span><span class="p">(</span><span class="n">filename</span><span class="p">);</span> <span class="kt">int</span> <span class="n">m</span> <span class="o">=</span> <span class="n">getMatrixM</span><span class="p">(</span><span class="n">filename</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="n">inner</span> <span class="p">(</span><span class="n">m</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="n">inner2</span> <span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">J</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">inner</span><span class="p">),</span> <span class="n">T</span><span class="p">(</span><span class="n">m</span><span class="p">,</span> <span class="n">inner2</span><span class="p">),</span> <span class="n">R</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">inner</span><span class="p">);</span> <span class="n">read</span> <span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="n">J</span><span class="p">);</span> <span class="n">transpose</span><span class="p">(</span><span class="n">J</span><span class="p">,</span> <span class="n">T</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">m</span><span class="p">);</span> <span class="n">ikjalgorithmTranspose</span><span class="p">(</span><span class="n">J</span><span class="p">,</span> <span class="n">T</span><span class="p">,</span> <span class="n">R</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">m</span><span class="p">);</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">R</span><span class="p">,</span> <span class="n">n</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Time:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 5m31.488s user 5m27.560s sys 0m1.812s</code></pre></div> <h3>Direct multiplication</h3> <p>One might think that transposing first is a bad idea, because you can do this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">ikjDirect</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">J</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">R</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">,</span> <span class="kt">int</span> <span class="n">m</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">m</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="k">register</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">R</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">J</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">J</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">k</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="n">R</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>I stopped execution after 15 minutes.</p> How to install Arch Linux 2013.10.01 //martin-thoma.com/install-arch-linux-2013-10-01/ Mon, 07 Oct 2013 03:19:05 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/install-arch-linux-2013-10-01 <p>I’ve watched the following video which explains pretty much everything there is to know:</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/BMgGUBDxCjo" frameborder="0" allowfullscreen=""></iframe> <p>You might also want to read the <a href="https://wiki.archlinux.org/index.php/Installation_Guide">Arch Linux Installation Guide</a>. The <a href="https://wiki.archlinux.de/title/Anleitung_f&uuml;r_Einsteiger">German guide</a> is also very good.</p> <p>I just like to add some notes. They are primarily for myself, so you really should read the installation guide or watch the video.</p> <p>The Arch Linux installation setup is command line based.</p> <h2>Keyboard layout</h2> <p>You can switch to a German keyboard layout with this command:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">loadkeys de</code></pre></div> <h2>Partitioning and mounting</h2> <p>You need a bootable partition and a swap partition (that is at least as big as much RAM you have). Partitioning can be done with <code>cfdisk</code> (configure disk).</p> <p>Check the result with</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">parted /dev/sda print fdisk -l</code></pre></div> <p>Afterwards:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">mkfs.ext4 /dev/sda1 mkfs.ext4 /dev/sda3 mkswap /dev/sda2 swapon /dev/sda2 mount /dev/sda1 /mnt mkdir /mnt/home mount /dev/sda3 /mnt/home/</code></pre></div> <h2>Getting internet</h2> <p>I only have WLAN at the moment, which makes things more difficult:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">wpa_passphrase <span class="s2">&quot;SSID&quot;</span> PASSWORD &gt; /etc/wpa_supplicant/wpa_supplicant.conf wpa_supplicant -i wlp4so -D wext -c /etc/wpa_supplicant/wpa_supplicant.conf -B dhcpcd wlp4s0</code></pre></div> <p>wlp4s0 is the wlan interface (which is wlan0 most of the time). You get it with <code>ip link</code>.</p> <p>I had a lot of fun at this point as you can see <a href="http://unix.stackexchange.com/questions/93851/can-i-connet-to-internet-with-one-pc-and-give-over-lan-switch-internet-to-othe">here</a>.</p> <h2>Install base system</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">packstrap -i /mnt base base base-devel</code></pre></div> <p>After accepting all defaults (by pressing enter) and letting it download:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">genfstab -U -p /mnt : sed <span class="s1">&#39;s/rw,realtime,data=ordered/defaults,realtime/&#39;</span> &gt;&gt; /mnt/etc/fstab arch-chroot /mnt nano /etc/locale.gen</code></pre></div> <p>Uncomment your language (from now on, your promt should be “sh-4.2#”).</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">locale</span><span class="o">=</span>gen <span class="nb">echo </span><span class="nv">LANG</span><span class="o">=</span>en_US.UTF-8 &gt; /etc/locale.conf <span class="nb">export </span><span class="nv">LANG</span><span class="o">=</span>en_US.UTF-8 ln -s /usr/share/zoneinfo/Europe/Berlin /etc/localtime hwclock --systohc --utc systemctl <span class="nb">enable </span>dhcpcd.service</code></pre></div> <p>Now edit and uncomment multilib. Then:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">mkinitcpio -p linux</code></pre></div> <p>Now set the password by entering <code>passwd</code>. Create your user:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">useradd -m -g users -G wheel -s /bin/bash moose passwd moose</code></pre></div> <p>Synchronise caches:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pacman -Syy</code></pre></div> <p>Install grub:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pacman -S grub-bios pacman -S os-prober grub-install /dev/sda grub-mkconfig -o /boot/grub/grub.cfg <span class="nb">exit</span> restart</code></pre></div> <p>Give yourself sudo:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pacman -S sudo nano /etc/sudoers</code></pre></div> <p>Add your user to the bottom section “User privilege specification”</p> <h2>Install GNOME</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pacman -S gnome xorg systemctl <span class="nb">enable </span>gdm.service</code></pre></div> <h2>MATE</h2> <p>Add the following to your /etc/pacman.conf:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">[mate] SigLevel = Optional TrustAll Server = http://repo.mate-desktop.org/archlinux/$arch</code></pre></div> <p>Run</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="c"># pacman -Syy</span> <span class="c"># pacman -S mate mate-extras</span></code></pre></div> <p>Lets see if I get an answer to <a href="https://bbs.archlinux.org/viewtopic.php?id=170911">some essential basic questions</a>.</p> Projects I never realized //martin-thoma.com/projects-never-realized/ Tue, 01 Oct 2013 23:41:37 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/projects-never-realized <p>The following is a collection of ideas for projects I had, but never realized. I would really love to do them, but they seem to be a little bit too time consuming to do them in my free time. Please send me an E-Mail if you would like to realize them!</p> <h2 id="book-portal">Book portal</h2> <p>I really miss a book recommendation portal. It should allow you to mark books you’ve read or started to read, let you rate and tag books. The tags should be created by users, similar to the system StackExchange uses. Tags might be funny”, “zombie”, “magic”, “romance”, “love”, … and users should rate for tags for books. In some general settings you define language(s) you know. Every book, which should be administrated by ISBN number if possible, should have information about the language. The portal should also see when books are only released with a new cover / collectors edition and notice that its the same story.</p> <p>With this information, it should recommend books and allow you to search books.</p> <p>Eventually you could connect to friends and let their ratings influence what you get.</p> <p>And, very important, it should let you follow series and/or authors. So you should be able to say “When there is a new book of the ‘Harry Potter’ series, send me an e-mail!” or “When there is a new book of the ‘Harry Potter’ series translated to ‘German’, send me an e-mail!”.</p> <h2 id="science-and-education-platform">Science and Education Platform</h2> <p>Sometimes, scientists get new insights that are able to influence millions. But until such a great invention or discovery is made, hundreds or thousands of people might have thought about the same problem. Today, with <abbr title="Massive open online courses"><a href="https://en.wikipedia.org/wiki/Massive_open_online_course">MOOCs</a></abbr> education in some fields is quite open to a lot of people. <a href="https://www.khanacademy.org/">Khan academy</a> offers many very basic courses, <a href="https://www.coursera.org/">Coursea</a> and <a href="https://www.udacity.com">Udacity</a> a few advanced ones. But the process of creating new content seems to be quite closed. <a href="https://en.wikiversity.org">Wikiversity</a> is more open, but very limited. For example, I think it is not possible to include <a href="../html5/graphic-filters/graphic-filters.htm">my graphic filter examples</a>. And it is not possible to track progress of students.</p> <p>I think it is necessary to gamify this. Both, students and educators, should get rewards. They might be only digital, but a student who can see the progress he makes might be much more interested in continuing a course. A teacher who can see the influence he has, who can see how students learn and where problems are might be much better able to improve his content and be motivated to do so.</p> <p>Also, scientists should not have to worry about presenting their studies. A lot of people know how to create graphics, some people know better about (the English) language and others are experts in LaTeX. If people were able to create requests online, get rewards for helping others and provide rewards to show that they really need help, I guess much better research could be made. Of course, this should be open.</p> <p>For every unit / paper, there should be definitions what is necessary to know. The topics should automatically be linked to content that provides the knowledge.</p> <p>It is very complex to plan such a system, because education in different languages / nations might be very different and ideas how to educate vary a lot. Even subtasks (creating a LaTeX editor, a graph that shows influence of papers / books by citation, creating an image editor, creating a reward system) are very difficult. And everything has to scale for millions of users. This means you would have to plan quite a lot before you could even think about implementation. For this project, you would need:</p> <ul> <li>Somebody, who has experience with online courses.</li> <li>A teacher for children.</li> <li>A teacher for teenagers.</li> <li>A teacher for students.</li> <li>Somebody, who has experience with gamification.</li> <li>Somebody, who has contacts to politics and knows how to advertise.</li> </ul> <h2 id="wikipedia-ai">Wikipedia AI</h2> <p>Try to categorize images in <a href="https://en.wikipedia.org/wiki/Category:Uncategorized_images">Category:Uncategorized images</a> or find images that have the wrong category / missing categories.</p> <h2 id="translations">Translations</h2> <p>I did some translation work some years ago for <a href="http://www.nongnu.org/lordsawar/">LordsAWar</a>. From a software point of view, this was a pain in the ass. Rosetta (part of Launchpad, for Ubuntu) is much better.</p> <p>Another idea that is much better is <a href="http://www.duolingo.com/">Duolingo</a>.</p> <p><a href="http://www.getlocalization.com/">getlocalization.com</a> might also be worth a try.</p> <h2 id="wiki-like-dictionary">Wiki-like Dictionary</h2> <p>Wikipedia is great, but the Wiktionaries suck. I would like to have a dictionary service. It should be working for all language combinations (English ↔ German; English ↔ French; German ↔ French; …). The data should initially be filled by computers, but then be improved / corrected by humans.</p> <h3 id="database">Database</h3> <p>It is basically a database with a nice interface.</p> <p>The database should have the following tables:</p> <ul> <li>Languages: LangID, Name in the language itself, icon</li> <li>Literature: LiteratureID, LangID, ISBN</li> <li>Words: WordID, Word, Normalized Occurences in Standard Literature</li> <li>WordPronounciation: WordPronounciationID, Pronounciation in phonetics, Pronounciation by a human <ul> <li>Pronounciation by a human should be stored on Wikipedia Commons</li> </ul> </li> <li>WordTags: WordTagID, Tag, Description in Markdown <ul> <li>Examples: Adjective, Substantive, male, genitiv, past, medicine …</li> </ul> </li> <li>TagTag: TagTagID, TagID, TagTag, Description in Markdown <ul> <li>Examples: Gender, Word-Class, Tense, Context, …</li> </ul> </li> <li>Tags2Words: T2WID, TagID, WordID</li> <li>Sentences: SentenceID, Sentence</li> <li>Words2Sentece: ID, SentenceID, WordID</li> <li>Definitions: ID, WordID, Definition, Image <ul> <li>Images should be stored on Wikipedia Commons</li> </ul> </li> <li>Translations: ID, WordID, TranslationID <ul> <li>Note that translations don’t have to be unique. There might be more than one correct translation for a word (e.g. “Bank”)</li> <li>Note that some translations might be more appropriate, depending on the context.</li> </ul> </li> <li>Users: UserID, DisplayName, E-mail, HashedPassword</li> </ul> <h3 id="initial-data">Initial Data</h3> <ul> <li>Wiktionaries</li> <li>For nouns: Lemmas of articles</li> </ul> <h3 id="features">Features</h3> <ul> <li>Downloadable minimal dataset for language combinations (e.g. on your smartphone in case you don’t have internet access). The most important words (2000 or so) should come with the audio data.</li> <li>Web search like dict.leo.org (e.g. <a href="http://dict.leo.org/?lp=ende&amp;search=bank">example search</a>)</li> <li>Forum to ask for translations, given context.</li> <li>Discussion pages for entries</li> <li>Moderators to “protect” entries.</li> <li>Ranking to find most important words which need some human work</li> </ul> <h2 id="distributed-universal-tagging-system">Distributed, Universal Tagging System</h2> <h3 id="tagging">Tagging</h3> <p>Most information can be displayed rather simple. A string that describes the kind of information and a bool / int / float / string / BLOB for the information itself and an identifier.</p> <p>For example, you can describe a product with the following labels:</p> <ul> <li>Identifier: “898a4c822ffc456fa7a417e500b2c05a”</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “ISBN-10”: “0141439513” (string)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “ISBN-13”: “978-0141439518” (string)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “Pages”: 480 (int)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “Publisher”: “Penguin Classics” (string)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “Category”: “Book” (string)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “Category”: “Literature” (string)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “Category”: ed054753e4b240a8aa1322ad348bf728 (identifier)</li> <li>“898a4c822ffc456fa7a417e500b2c05a”, “VIEW”: 0839c5beac414fb19c400b6ca0372388 (identifier)</li> <li>Identifier: “ed054753e4b240a8aa1322ad348bf728”</li> <li>“ed054753e4b240a8aa1322ad348bf728”, “Name”: “Literature”</li> <li>“ed054753e4b240a8aa1322ad348bf728”, “Category”: “Books”</li> </ul> <p>As you can see, it is possible to create nested categories with this structure. You an also create lists this way.</p> <p>Now clients should store information like this and share it.</p> <h3 id="views">Views</h3> <p>When information is presented like this, it is quite useless. But what about this kind of presentation:</p> <div style="width: 277px" class="wp-caption aligncenter"><a href="../images/2013/10/pride-and-prejudice-infobox.png"><img src="../images/2013/10/pride-and-prejudice-infobox.png" alt="Pride and prejudice infobox" width="" height="" class="size-full wp-image-76576" /></a><p class="wp-caption-text">Pride and prejudice infobox (defined <a href="https://en.wikipedia.org/wiki/Template:Infobox_book">here</a>)</p></div> <p>Or, for example <a href="http://ark.intel.com/compare/75133,50176">ark.intel.com</a>:</p> <div style="width: 653px" class="wp-caption aligncenter"><a href="../images/2013/10/intel-ark-compare.png"><img src="../images/2013/10/intel-ark-compare.png" alt="Intel Arc compare processors" width="" height="" class="size-full wp-image-76577" /></a><p class="wp-caption-text">Intel Arc compare processors</p></div> <p>So another required feature of such a client are “views”. A view is defined by an identifier (so that you can tag views just like any other object) and an HTML template. Objects could have labels called “VIEW” with type identifier that tell the client which view should be added.</p> <h3 id="distribution">Distribution</h3> <p>There are plenty of cool tools out there (Amazon recommendations, <a href="http://ark.intel.com/">ark.intel.com</a> to compare Intel processors, <a href="http://de.blackberry.com/smartphones/compare.html">blackberry</a> allows you to compare their phones, Wikipedia info boxes, …). But most of them are very ristricted. For example, the way I compare smartphones is not fundamentally different from the way I compare processors. Yes, the attributes differ. But basically it is creating a table with all the information. Also, Intel does not provide information about AMD processors.</p> <p>So we need a way to get and share information. XML is the way-to-go for centralized computer systems. Maybe they can also be used to realize what I’m thinking about. But I think a problem that has to be solved is that we don’t have a single source for all information that we trust in. We have networks of trust. When Intel says A and a friend says B about an Intel processor, I guess I will rather believe A. But when Intel does not provide some information about a processor and a friend says B, but a person I don’t know says C, I’ll believe B. But when thousands of people say C and my friend says B, I might rather believe C.</p> <p>It’s getting complicated, right? Maybe the processor example is not good, as there is much information and information is either right or wrong. But lets say we talk about genre of movies. This might be much more difficult as there is no “definitely right” or “definitely wrong”. Multiple answers might be right.</p> <p>So every information has also have to carry information about who thinks it is right. And you have to be able to define networks you trust in. Perhaps you could create “people objects” that can also be labeled. “Your” object had to be protected so that only you could add “friend of” labels or “I trust” labels or something like this.</p> <h2 id="python-code-search">Python Code Search</h2> <p>Do you know <a href="https://codesearch.debian.net/">Debian Code Search</a>? Michael Stapelberg, the creator of it, described how he did it in <a href="https://codesearch.debian.net/research/bsc-thesis.pdf">his bachelor’s thesis</a>.</p> <p>I would like to have the same for Python code. This could be done by downloading all Python packages. I already did this part, see <a href="//martin-thoma.com/analyzing-pypi-metadata/">Analyzing PyPI Metadata</a> and the follow-up post which is still on my TODO-list to be published (see <a href="https://github.com/MartinThoma/MartinThoma.github.io/blob/source/_drafts/2015-12-07-analyzing-pypi-metadata-2.md">draft</a>).</p> <p>It would also be possible to add GitHub repositories.</p> <h2 id="commentit">Comment.it</h2> <p>Sometimes, I just want to add my 2ct to something. I would like to have a central website / service - preferable as a browser plugin - with which I can add comments to other websites on an URL basis (including anchors for maximum exactness). Then I could read what other people think of something, even if there is no comments section.</p> <h2 id="charity-search--find">Charity Search &amp; Find</h2> <p>“Vermittlung” (<a href="http://ell.stackexchange.com/q/80159/11067">recruiting?</a>) of people who have the ability needed for charity organizations.</p> <p>People:</p> <ul> <li>profile / abilities <ul> <li>Text, grade / level?</li> <li>tags?</li> </ul> </li> <li>location</li> <li>Karma?</li> <li>Filtering</li> </ul> <p>Projects:</p> <ul> <li>Profile page for each project</li> <li>photos</li> <li>members / oranization / roles / karma / contributers</li> <li>domain</li> </ul> <p>Other elements:</p> <ul> <li>Forum: phpBB? Disqus?</li> <li>File uploads: Imgur?</li> <li>Calendar</li> <li>E-Mail list: GNU Mailman?</li> <li>Surveys: Limemonkey?</li> </ul> <h2 id="database-administration-interface">Database administration interface</h2> <p>It would be nice to have a database administration interface similar to phpMyAdmin for other databases, too (postgres, sqlite). One could also make it a web service (dbadmin.io or something similar).</p> <h2 id="chrome">Chrome</h2> <p>I had some <a href="../how-chrome-could-be-improved-2nd-post/">ideas how to improve Chrome</a>.</p> <h2 id="mate">MATE</h2> <p>After the changes in desktop environments, <a href="https://en.wikipedia.org/wiki/MATE_(software)">MATE</a> got my favorite desktop environment. Although I was more happy with GNOME 2.6.</p> <ul> <li>Adding the drag-and-drop effect that creates a new window from an tab, known from Chrome, to Terminal and Pluma (gEdit).</li> <li>Creating a LaTeX plugin for Pluma that auto-completes the environments.</li> </ul> <h2 id="latex-tools">LaTeX Tools</h2> <p>I would like to create online tools (pure HTML/CSS/JavaScript) that make the following tasks simpler.</p> <ul> <li>A table editor. I know <a href="http://truben.no/latex/table/">Trubens table tool</a>, but this tool does not allow to combine cells. Also, the site is down quite often.</li> <li>A Ti<em>k</em>Z editor.</li> <li>An editor for bibliography.</li> <li>A LaTeX source code beautifier.</li> <li>A LaTeX-aware spell checker. This spell checker could probably use aspell, but it would have to filter LaTeX code.</li> </ul> <p>Also, I would like to create an app that helps users to create formulas. This app should run on smartphones and on tablets. I don’t think that this can be done with pure JavaScript.</p> <h2 id="open-hardware">Open Hardware</h2> <p>I’m fascinated by the idea of open hardware. That means that you publish plans of something and maybe also how to create it. Although I don’t have any experience in this field, I can think of some interesting projects. One way to support open hardware would be to create an education and science platform, like the one I’ve described above.</p> <h3 id="open-internet">Open Internet</h3> <p>I guess most smartphone users know this situation: You go to a friend / on vacation and you don’t have WLAN. This means you have to use mobile internet, which is expensive. If you’re in an area where not many people live, it is ok. If you’re in a big city, it is not. There are so many people who have an internet connection and a router which already establishes a WLAN. You can see them, but not use the connection! What a shame!</p> <p>What we would need is a device with the following attributes:</p> <ul> <li>Simplicity <ul> <li>It has to be a <a href="https://en.wikipedia.org/wiki/DSL_modem">DSL modem</a> and a <a href="https://en.wikipedia.org/wiki/Router_(computing)">router</a> combined, eventually also a <a href="https://en.wikipedia.org/wiki/DSL_filter">DSL filter</a>.</li> <li>Everything has to be configurable via web interface. This interface has to be VERY GOOD.</li> <li>You should be able to get a backup file via web interface that contains every single configuration. This file should be an good documented XML file. The documentation should contain example data.</li> <li>Every setting should have its own url, just like in Google Chrome.</li> <li>As many self-tests that give meaningful messages as possible: <ul> <li>A LED that indicates if the device has power.</li> <li>Ethernet jack should glow if a device is connected and blink if data is send.</li> <li>A software test via web interface that checks if internet connection is available.</li> <li>Direct feedback when you enter wrong / malformed credentials.</li> </ul> </li> <li>A reset button that restores the software completely from non-erasable memory.</li> <li>Small memory and rechargeable battery that allows you to download router software updates when the battery is full.</li> <li>A user manual with pictures that explains what to do to get internet.</li> </ul> </li> <li>Functionality and requirements <ul> <li>It has to be able to create a WLAN.</li> <li>It has to be fast. I think currently 802.11n is with 450 Mbit/s the best you can get for WLAN and 1000 Mbit/s for Ethernet</li> <li>At least one Ethernet jack.</li> <li>It should be secure (WPA2, eventually don't support WEP and WPA).</li> <li>Reasonable energy consumption and no active fans.</li> <li>A standardized power supply unit that can be bought without buying a new device.</li> </ul> </li> <li>Box - how it looks <ul> <li>The case should be robust.</li> <li>You should be able to mount it to a wall or to lay it on the floor.</li> </ul> </li> </ul> <p>I don’t think it is necessary to support VoIP, ISDN and Surf Sticks.</p> <p>Now the special part: It should allow you to create a WLAN that others can use by registering in a service. The device should guarantee that you get the bandwidth, in case you need it. But if you have free bandwidth, others should be able to use it. Of course, this function should also protect you from legal trouble. An essential problem is keeping you from legal trouble while making sure that nobody uses the system to betray external users. But when you solve this problem, I guess it would be quite easy to establish free WLAN in all bigger cities. A great chance for tourism and a backup-option for you when your internet connection breaks.</p> <p>The service should also allow the user to register the free WLAN online. An app should download these locations and be able to navigate a user to the next free WLAN.</p> <p>Ah and of course everything in there should be free. This piece of hardware is critical for your internet access. If you want to be sure that you don’t get under surveillance by an attack on this piece of hardware, it would be good to know that some smart people had the possibility to check if everything is fine with this hardware.</p> <h3 id="work-computers">Work computers</h3> <p>Today, we have a lot of computers that are used for very, very simple work. The most computing intensive part might be large Excel sheets. So basically, they don’t need any improvements in hardware for years. But the few things they do, need to be done well. Security is important. It is also important that things are stable and don’t change a lot. And what they do should be fast. Loading times are almost not acceptable.</p> <p>I guess many tasks could be done within a browser. So work that needs heavy computation can be done on a stronger machine (the cloud - not necessarily outside of the company).</p> <p>Why hasn’t any big company like <a href="https://en.wikipedia.org/wiki/General_motors">General Motors</a>, <a href="https://en.wikipedia.org/wiki/General_Electric">General Electric</a>, <a href="https://en.wikipedia.org/wiki/Walmart">Wallmart</a> or even countries that have thousands of schools and government employees tried to create such a computer that is really reliable, robust and cheap (energy and because it can be produced it can be produced in very big numbers)?</p> <p>Here is what I think should be ok:</p> <ul> <li>processor with low power consumption (700 MHz or more)</li> <li>2 GB of RAM (I guess you might now think of this <a href="https://en.wikiquote.org/wiki/Bill_Gates#Misattributed">missatributed Bill Gates quote</a> … but with <code>cat /proc/meminfo</code> you can see how much you currently use).</li> <li>30 GB SSD: Important information should be stored on a computer that is protected very well against data loss. A SSD is silent and can read content very fast. Ideally, only the <abbr title="operating system">OS</abbr> is stored on the employees computer.</li> <li>VERY silent fan, if possible non at all.</li> <li>Big monitor with high resolution, because those people have to work all day with the computer and low quality speakers.</li> <li>Good and silent keyboards (like the <a href="http://codekeyboards.com/">CODE keyboard</a>).</li> <li>Network card.</li> <li>Graphic card that allows the high resolution display.</li> </ul> <p>This is just a quick thought. I think such a system should contain some reference software that has to run fluidly. The software should also be open, of course. I think the following should be enough:</p> <ul> <li>Linux based OS (e.g. <a href="https://en.wikipedia.org/wiki/Debian">Debian</a>)</li> <li>Basic command line tools (bash, grep, find, cat, vim)</li> <li>Desktop manager with classic desktop metaphor (e.g. <a href="https://en.wikipedia.org/wiki/MATE_(desktop_environment)">MATE</a>)</li> <li>File manager with access to a network drive (e.g. Caja or Nautilus)</li> <li>Modern Browser (Firefox or Chrome)</li> </ul> <p>Tasks that can (and should) be done via browser are:</p> <ul> <li>E-mails: e.g. <a href="https://en.wikipedia.org/wiki/Roundcube">Roundcube</a></li> <li>Excel: Hmmm … I know that <a href="https://drive.google.com">Google Docs</a> offers some similar stuff. Bug I guess it can’t replace Microsoft Excel by now. I don’t know if there are any self-hosted services</li> <li>Word: e.g. <a href="http://etherpad.org/">Etherpad</a></li> <li>Outlook: e.g. <a href="http://owncloud.org/">OwnCloud</a></li> <li>LaTeX: e.g. <a href="https://github.com/alabid/flylatex">FlyLaTeX</a></li> <li>Geographic information systems: I don’t know if there is software online. But I guess with OpenStreetMaps it should not be too difficult to create it. <a href="http://www.esri.com/software/arcgis/arcgisonline">ArcGis</a> seems to be one solution.</li> </ul> <p>Basically, you can do almost everything with a web application. So the client can get quite slim. But although you could probably do everything with a self hosted client/server solution, those solutions don’t always exist yet.</p> <p>Tasks that should not be done via browser might be:</p> <ul> <li>Professional video/audio editing: I guess you need more than one monitor to display all relevant information.</li> <li>Programming: Although I have seen <a href="https://c9.io/">Cloud9</a>, I doubt that programming in the cloud can be convenient in the next years. How does bug fixing work? How about manual testing? Whats with parallel execution?</li> <li>Messaging: If you want to use encrypted communication (e.g. E-mail with PGP) you should probably do the encryption on your machine.</li> </ul> <p>Hmmm … astonishingly, I can currently not think of more tasks.</p> <h3 id="not-so-smart-phone">Not so smart phone</h3> <p>Do you remember the good old days when your cell phone wasn’t essentially a small PC? I’ve bought a smartphone a while ago (<a href="../nexus-4/">article</a>), but I still see reasons to have a cell phone:</p> <ul> <li>Battery life: My Motorola W156 had a battery with only 940 mAh, but 465 hours stand-by time. If it had 3100 mAh as the <a href="https://en.wikipedia.org/wiki/Samsung_Galaxy_Note_II">Samsung Galaxy Note II</a>, it would have a standby time of 1534 hours! That are about 64 days!</li> <li>Security: Have you ever heard of somebody hacking a device that can only phone and send SMS?</li> <li>Cost: The Motorola W156 costs 25 Euro on Amazon.</li> <li>Robustness: A friend of mine put her <a href="https://en.wikipedia.org/wiki/Nokia_3310">Nokia 3310</a> accidentally in the washing machine. After that, she removed the battery, let it dry for a week, put the battery back. It worked. What the hell!?! (See also: <a href="http://weknowmemes.com/2012/02/our-love-is-forever-so-here-is-a-nokia/">Nokia is forever</a> and <a href="http://knowyourmeme.com/memes/indestructible-nokia-3310">Indestructible Nokia 3310 meme</a>)</li> <li>Size: Modern smartphones are a little bit uncomfortable to phone with. They are too big, although they are very thin. A size of 114 x 43 x 14 mm is fine, maybe a little bigger is also ok.</li> </ul> <p>The needed functionality is:</p> <ul> <li>Phone with good quality</li> <li>Send SMS (and repetedly try to do so if no net is available)</li> <li>Store about 100 contacts</li> <li>Save about 100 SMS</li> <li>Load battery via micro USB (<a href="https://en.wikipedia.org/wiki/Common_External_Power_Supply">Common External Power Supply</a>)</li> <li>If not too complicated: Let me back up all data on the phone via this micro-USB slot and let me also restore such a backup</li> <li>3.5mm phone jack for using a headset</li> </ul> <p>&lt;/ul&gt;</p> <p>What is not needed:</p> <ul> <li>Camera, Flashlight</li> <li>Internet access, Bluethooth, NFC, …</li> <li>Multi-colored display: B/W screen is just ok</li> <li>Fingerprint scanner</li> </ul> <h3 id="light-alarm-clock">Light Alarm Clock</h3> <p>An alarm clock which wakes you up with light.</p> <p>Features:</p> <ul> <li>Set multiple alarms</li> <li>(Non-lit) display which shows <ul> <li>the time</li> <li>time to the next alarm in <code>X d - Y h - Z m</code> format</li> </ul> </li> <li>Batteries</li> <li>Be able to set multiple alarms: <ul> <li>Choose days for which the alarm rings</li> <li>Choose dimming profile for the alarm (smooth - aprubt)</li> </ul> </li> <li>Be able to change the (dimming) light which is inside</li> </ul> Bitcoin //martin-thoma.com/bitcoin/ Wed, 11 Sep 2013 20:53:51 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/bitcoin <blockquote>Bitcoin [...] is a cryptographic currency where the creation and transfer of bitcoins is based on an open-source cryptographic protocol that is <strong>independent of any central authority</strong>. Bitcoins can be transferred through a computer or smartphone without an intermediate financial institution. The concept was introduced in a 2008 paper by a pseudonymous developer known only as "Satoshi Nakamoto", who called it a <strong>peer-to-peer, electronic cash system</strong>. The processing of Bitcoin transactions is secured by servers called bitcoin miners. These servers communicate over an internet-based network and confirm transactions by adding them to a ledger which is updated and archived periodically using peer-to-peer filesharing technology. In addition to archiving transactions, each new ledger update creates some newly minted bitcoins. The number of new bitcoins created in each update is halved every 4 years until the year <strong>2140</strong> when this number will round down to zero. At that time no more bitcoins will be added into circulation and the total number of bitcoins will have reached a <strong>maximum of 21 million bitcoins</strong>. To accommodate this limit, each bitcoin is subdivided down to eight decimal places; forming <strong>100 million smaller units</strong> called satoshis. In August 2013 Germany's Finance Ministry subsumed Bitcoins under the term "unit of account"&mdash;a financial instrument&mdash;though not as e-money or a functional currency. Although bitcoin is promoted as a digital currency, many commentators have criticized bitcoin's volatile exchange rate, relatively inflexible supply, high risk of loss, and minimal use in trade.</blockquote> <p>Source: <a href="https://en.wikipedia.org/w/index.php?title=Bitcoin&amp;oldid=571455676">Wikipedia</a></p> <p>Sounds interesting, doesn’t it? I’d like to share my thoughts about some aspects of Bitcoin. Please note that I’m neither an economics student, nor did I read the specifications of Bitcoin.</p> <h2>Security of Bitcoin</h2> <h3>Data loss</h3> <p>Once in a while, hard discs crash. If you’re unlucky, you will lose all your data. This could mean you lose your Bitcoin wallet, so you lose your money. There is absolutely no way to get the money back. It’s lost. Just like if you’ve lost bank notes in a big city. You will never get it back (<a href="http://bitcoin.stackexchange.com/q/116/6721">source</a>).</p> <p>BUT, unlike with bank notes, nobody else will get it. These Bitcoins are lost and nobody can do anything against that. I think that means <strong>after 2140 the number of active Bitcons will drop</strong>! This is called a <a href="https://en.wikipedia.org/wiki/Deflation">deflation</a> with normal money. But as you can subdivide every bitcoin in as small pieces as you like, I’m not sure what this means for economy.</p> <h3>Attacks</h3> <p>When money is involved, there will always be people who try to profit from that. So you have to think about security of Bitcoins.</p> <h4>System attacks</h4> <p>For me, a system attack is an attack where somebody tries to break the system. He does NOT want to profit from the system, but he wants to harm all people who use it.</p> <p>The only attack I’ve found is a 51%-attack (<a href="https://en.bitcoin.it/wiki/Weaknesses#Attacker_has_a_lot_of_computing_power">source</a>). This means, in long term you have to have more than 50% of the computing power of the total bitcoin network. So if there is a dramatic change in computing power, this might make Bitcoin as a system insecure. Also, in short term with much luck you might also take down the network with less computing power (<a href="http://bitcoin.stackexchange.com/a/10937/6721">source</a>).</p> <p>But the more people participate, the more unlikely it gets. And this problem might our current system also have. If somebody manages to get MUCH more computing power, he could break encryption. This means, all bank transactions could at least be read by this attacker, if not manipulated.</p> <h4>Theft</h4> <p>Theft is possible by stealing your credentials. This can be done by infecting your computer with a virus, just like it can be done today with your bank account if you use online banking (or with the computers of banks, though that should be much more difficult).</p> <p>Also, the software you use for Bitcoin transactions might have errors.</p> <h2>Money laundering</h2> <p>It seems to be a big problem of Bitcoin that money laundering might be easy. You can’t close a criminals account, you cannot stop criminals using Bitcoin for illegal operations.</p> <p>But what can you do with the current currency against that? Not much, when the money gets abroad.</p> <h2>Credits</h2> <p>You can’t give credits as banks do it today with Bitcoin. If I understand it correctly, the “Common Equity Capital Ratio” has to be at least 3.5% in 2013 (<a href="https://en.wikipedia.org/wiki/Basel_III">source</a>). In other words: banks are allowed to give more than 27x the amount of money they actually have! Now I’m very uncertain if I’m here correct, but I think this was an important reason why the financial crisis happened. This would not have been possible with Bitcoin! With Bitcoin, you can only give credit for money you currently have. No cent … uhmm … Sotisho more than that.</p> <p>BUT: I really don’t know if this would be better. I guess it would be extremely difficult for states to get money. There would be the need of heavy restructuring in how we finance our countries.</p> <h3>Interest</h3> <p>A problem with credits in the Bitcoin-system would be that it is very difficult to estimate what the result of the interest would be.</p> <p>As there are “only” 21 million Bitcoins, it would bet possible that the sum of all dept is more than available Bitcoins. Can it be legal to force people to pay when you know that at least one technically can’t pay at the end? This problem seems not to exist in the current system, as they always print new money.</p> <h2>Wages</h2> <p>At the moment, employed people have to fight in unions for more money. They really need it, because inflation happens all the time. So just to keep the current situation, employees have to do something.</p> <p>With Bitcoin, the situation might change. As we produce more and more every year, a deflation would be likely. This means, bosses would have to cut loans to keep the situation the same. But it is much more difficult to change the bills you pay. People will not blindly accept less money on their accounts per month. Unlike today, when people are basically ok when they get a compensation for inflation.</p> <h2>See also</h2> <ul> <li><a href="https://www.bitcoin.de/de">Bitcoin.de</a>: You can see how much 1 Bitcoin is worth in Dollar / Euro.</li> <li>bitcoin.stackexchange.com: <ul> <li><a href="http://bitcoin.stackexchange.com/q/13215/6721">What can we do if Bitcoin is used as money laundering?</a></li> <li><a href="http://bitcoin.stackexchange.com/q/122/6721">Will we ever need smaller amounts of Bitcoin than a Satoshi?</a></li> </ul> </li> <li><a href="https://medium.com/the-magazine/23e551c67a6">On the Matter of Why Bitcoin Matters</a></li> </ul> How to apply the Viterbi algorithm //martin-thoma.com/apply-viterbi-algorithm/ Wed, 11 Sep 2013 17:46:22 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/apply-viterbi-algorithm <p>The goal of the Viterbi algorithm is find the most likely sequence of hidden states given some observed events.</p> <p>Lets say this is your <abbr title="Hidden Markov model">HMM</abbr>:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/09/hidden-markov-model-abc-2.png"><img src="../images/2013/09/hidden-markov-model-abc-2.png" alt="A hidden Markov model (HMM) example" width="" height="" class="size-full wp-image-76518" /></a><p class="wp-caption-text">A hidden Markov model (HMM) example</p></div> <p>We always start in \(x\) and always end in \(z\).</p> <p>Now you observed the sequence \(O_1 = BAB\). What is the most likely sequence that would generate this path?</p> <p>Candidates are:</p> <ul> <li>xxyz</li> <li>xyyz</li> <li>xyzz</li> </ul> <p>If you’re learing this because you will write the exam at KIT, you might have such an diagram:</p> <div style="width: 761px" class="wp-caption aligncenter"><a href="../images/2013/09/viterbi-algorithm.png"><img src="../images/2013/09/viterbi-algorithm.png" alt="Scheme of the Viterbi algorithm" width="" height="" class="size-full wp-image-76520" /></a><p class="wp-caption-text">Scheme of the Viterbi algorithm</p></div> <p>In this case, the bold path is the Viterbi path. You can see this when you get backwards from the last state:</p> <p>\(\frac{1}{125} \cdot 1 \cdot 0.2 &gt; \frac{9}{2500} \cdot 0.8 \cdot 0.2\). After this step, you only have one choice. So the Viterbi path is xyzz.</p> <p>Please note that there might be multiple paths with the highest possibility.</p> <p>As every state depends only on the state before, you can get the most likely path step by step. In every step, you calculate how likely it is that you end up in state x, state y, state z. After that, it doesn’t matter how you got there. So you always have to expand those three nodes. You will get 9 following states, but only three of them matter (for each resulting state, the paths that had the highest probability leading there).</p> <h2 id="see-also">See also</h2> <ul> <li><a href="https://en.wikipedia.org/wiki/Viterbi_algorithm">Wikipedia</a></li> </ul> How do I calculate a Histogram equalization? //martin-thoma.com/calculate-histogram-equalization/ Wed, 11 Sep 2013 13:17:39 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/calculate-histogram-equalization <p>Let’s say you have the following greyscale image:</p> <p><code>$A = \begin{pmatrix} 255 &amp; 50 &amp; 255\\ 0 &amp; 50 &amp; 50 \end{pmatrix}$</code></p> <h2>Histogram</h2> <p>Now the histogram is a function <code>$H: [0,255] \rightarrow \mathbb{N}_0$</code>.</p> <p>The histogram of <code>$A$</code> is</p> <p><code>$H(x) := \begin{cases} 1 &amp;\text{, if } x = 0\\ 3 &amp;\text{, if } x = 50\\ 2 &amp;\text{, if } x = 255 \end{cases}$</code></p> <h2>Accumulated histogram</h2> <p>The accumulated histogram <code>$H_\alpha: [0,255] \rightarrow \mathbb{N}_0$</code> is defined as</p> <p><code>$H_\alpha(x) := \sum_{i=0}^x H(i)$</code></p> <p>This means, in the given example you get</p> <p><code>$H_\alpha(x) := \begin{cases} 1 &amp;\text{, if } x &lt; 50\\ 4 &amp;\text{, if } 50 \leq x &lt; 255\\ 6 &amp;\text{, if } x = 255 \end{cases}$</code></p> <h2>Normalized histogram</h2> <p>The normalized histogram is defined as <code>$H_n(x) := \mathrm{round}(\frac{255}{w \cdot h} \cdot H_\alpha(x))$</code> where <code>$w$</code> is the width of the image and <code>$h$</code> is the height of the image.</p> <p>In our example it’s:</p> <p><code>$H_n(x) := \begin{cases} 43 &amp;\text{, if } x &lt; 50\\ 170 &amp;\text{, if } 50 \leq x &lt; 255\\ 255 &amp;\text{, if } x = 255 \end{cases}$</code></p> <p>So the resulting image is</p> <p><code>$A = \begin{pmatrix} 255 &amp; 170 &amp; 255\\ 43 &amp; 170 &amp; 170 \end{pmatrix}$</code></p> <h2>See also</h2> <ul> <li><a href="http://www.songho.ca/dsp/histogram/histogram.html">Some code</a></li> <li><a href="http://www.csce.uark.edu/~jgauch/5683/notes/ch03b.pdf">Code and examples</a></li> </ul> Calculations with quaternions //martin-thoma.com/calculations-with-quaternions/ Mon, 09 Sep 2013 14:45:17 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/calculations-with-quaternions <p><a href="https://en.wikipedia.org/wiki/Quaternion">Quaternions</a> are an expansion of the concept of complex numbers on structures with four (instead of two) components. A quaterion <code>$h$</code> can be written as a vector or in the form of <code>$h = h_0 + ih_1 + j h_2 + kh_3$</code>, where <code>$i, j$</code> and <code>$k$</code> are related to the <code>$i$</code> in complex numbers. Accordingly <code>$h_0$</code> is often called real part and h_1, h_2, h_3 are called imaginary part of a quaternion.</p> <p>For <code>$i, j$</code> and <code>$k$</code> the following rules are applied:</p> <p><code>$i^2 = j^2 = k^2 = -1$</code> and <code>$ijk=-1$</code></p> <h2>Basic rules</h2> <p>From these rules follows: <code>$\begin{align} ij &amp;= k\\ ji &amp;= -k\\ jk &amp;= i\\ kj &amp;= -i\\ ki &amp;= j\\ ik &amp;= -j \end{align}$</code></p> <p>(<a href="http://math.stackexchange.com/q/487245/6876">proof</a>)</p> <h2>Multiplication</h2> <p>Now, obviously quaternions multiplication is not commutative: <code>$ij = k \neq -k = ji$</code></p> <p>But for numbers in <code>$\mathbb{R}$</code>, it is commutative (<a href="http://math.stackexchange.com/q/488271/6876">proof</a>).</p> <p>The multiplication is:</p> <p><code>$\begin{align} x y &amp;=( x_0 y_0 - x_1 y_1 - x_2 y_2 - x_3 y_3)\\ &amp;+( x_0 y_1 + x_1 y_0 + x_2 y_3 - x_3 y_2) \mathrm i\\ &amp;+( x_0 y_2 - x_1 y_3 + x_2 y_0 + x_3 y_1) \mathrm j\\ &amp;+( x_0 y_3 + x_1 y_2 - x_2 y_1 + x_3 y_0) \mathrm k \end{align}$</code></p> <h3>Calculating multiplicative inverse</h3> <p>This means, when you’re given an element <code>$x = x_0 + x_1 \mathrm i + x_2 \mathrm j + x_3 \mathrm k$</code> its inverse <code>$y$</code> can be calculated by solving the following linear system of equations:</p> <p><code>$\begin{align} x_0 y_0 - x_1 y_1 - x_2 y_2 - x_3 y_3 &amp;= 1\\ x_0 y_1 + x_1 y_0 + x_2 y_3 - x_3 y_2 &amp;= 0\\ x_0 y_2 - x_1 y_3 + x_2 y_0 + x_3 y_1 &amp;= 0\\ x_0 y_3 + x_1 y_2 - x_2 y_1 + x_3 y_0 &amp;= 0\\ \end{align}$</code></p> <p>which can be written as:</p> <p><code>$\left(\begin{array}{cccc|c} x_0 &amp; -x_1 &amp; -x_2 &amp; -x_3 &amp; 1\\ x_1 &amp; x_0 &amp; -x_3 &amp; x_2 &amp; 0\\ x_2 &amp; x_3 &amp; x_0 &amp; -x_1 &amp; 0\\ x_3 &amp; -x_2 &amp; x_1 &amp; x_0 &amp; 0 \end{array}\right).$</code></p> <p>According to <a href="http://www.mathworks.de/de/help/aeroblks/quaternioninverse.html">mathworks</a> it is</p> <p><code>$y = \frac{x_0 - \mathrm i x_1 - \mathrm j x_2 - \mathrm k x_3}{x_0^2 + x_1^2 + x_2^2 + x_3^2}$</code></p> <h2>More</h2> <h3>Conjugate</h3> <p>Just like the complex conjugate is defined as</p> <p><code>$\overline{z} = a - ib$</code> with <code>$z=a+ib$</code></p> <p>the conjugate of quaternions is defined as</p> <p><code>$\bar x := x_0-x_1\mathrm i-x_2\mathrm j-x_3\mathrm k$</code> with <code>$x=x_0+x_1\mathrm i+x_2\mathrm j+x_3\mathrm k$</code></p> <h3>Rotating points</h3> <p>Quaternions can be used to rotate points. It works like this:</p> <p><code>$x' = q x \overline{q}$</code></p> <p>Pretty simple, isn’t it?</p> <p>For example, if you had the point (2,0,0) and you wanted to rotated it by <code>$q = (\frac{\sqrt{2}}{2}, 0, \frac{\sqrt{2}}{2}, 0)$</code> you would transform (2,0,0) to (2i+0k+0j) and calculate</p> <p><code>$\begin{align} x' &amp;= q x \overline{q}\\ &amp;= (\frac{\sqrt{2}}{2}+\frac{\sqrt{2}}{2} \mathrm j) \cdot 2 \mathrm i \cdot (\frac{\sqrt{2}}{2} - \frac{\sqrt{2}}{2} \mathrm j)\\ &amp;= (\sqrt{2} \mathrm i + \sqrt{2} \mathrm{ji}) \cdot (\frac{\sqrt{2}}{2} - \frac{\sqrt{2}}{2} \mathrm j)\\ &amp;= (\sqrt{2} \mathrm i - \sqrt{2} \mathrm k) \cdot (\frac{\sqrt{2}}{2} - \frac{\sqrt{2}}{2} \mathrm j)\\ &amp;= \mathrm i - \mathrm{ij} - \mathrm k + \mathrm{kj}\\ &amp;= \mathrm{i - k -k - i}\\ &amp;= -2 \mathrm k\\ &amp;\Rightarrow x' = (0,0,-2) \end{align}$</code></p> <h3>Rotation matrix to quaternion</h3> <p>Let <code>$M$</code> be a rotation matrix and <code>$m_{ij}$</code> be an entry of this matrix.</p> <h4>General rule</h4> <p>\begin{align} s &amp;= \frac{1}{2} \sqrt{1 + \sum_{i=1}^3 m_{ii}}<br /> x &amp;= \frac{m_{32} - m_{23}}{4s}<br /> y &amp;= \frac{m_{13} - m_{31}}{4s}<br /> z &amp;= \frac{m_{21} - m_{12}}{4s} \end{align}</p> <p>resulting in the quaternion <code>$(s, x, y, z)$</code>.</p> <h4>Special rule</h4> <p>A rotation matrix</p> <p><code>$R_y = \begin{pmatrix} \cos(\theta) &amp; 0 &amp; \sin(\theta)\\ 0 &amp; 1 &amp; 0\\ -\sin(\theta) &amp; 0 &amp; \cos(\theta) \end{pmatrix}$</code></p> <p>can be transformed to a quaternion</p> <p><code>$q = (\cos(\frac{\theta}{2}), \vec u \sin (\frac{\theta}{2}))$</code></p> <p>where <code>$\vec u$</code> describes the axis you rotate by.</p> <p>In this case <code>$R_y$</code> is the y-axis, so <code>$\vec u = \begin{pmatrix}0\\1\\0\end{pmatrix}$</code>.</p> Informatik am KIT //martin-thoma.com/informatik-am-kit/ Sat, 07 Sep 2013 11:41:05 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/informatik-am-kit <p>Ich werde immer wieder gefragt, wie Informatik am KIT ist. Was kann ich über Karlsruhe erzählen? Wieviel Praxis bekommt man in einem Informatik-Studium am KIT?</p> <p>Leider denke ich nicht, das ich wirklich gut darüber schreiben dann, da ich nur „Informatik I“ an der Uni Augsburg gehört habe. Sonst war ich nur am KIT. Auch über Karlsruhe kann ich nicht so viel erzählen, wie man sich vielleicht denkt. Ich bin meistens am studieren. Daher habe ich von Karlsruhe außerhalb der Innenstadt bisher wenig gesehen.</p> <p>Ein paar Anhaltspunkte könnte die <a href="https://de.wikipedia.org/wiki/Karlsruher_Institut_f%C3%BCr_Technologie">Wikipediaseite des KIT</a> sowie die <a href="http://www.einstieg-informatik.de/index.php?article_id=162&amp;hid=55">einstieg-informatik.de-Seite</a> geben.</p> <p>Genug allgemeines bla-bla. Nun lasse ich die Disclaimer-Sätze (meinem Eindruck nach, ich kenne eigentlich nur das KIT und habe keine aussagekräftigen Vergleiche, …) weg und erzähle etwas über Karlsruhe und das KIT.</p> <h2>Das Studium</h2> <h3>Allgemeines</h3> <p>Die Regelstudienzeit des Bachelor-Informatik-Studium beträgt 6 Semester und 180 <a href="https://de.wikipedia.org/wiki/European_Credit_Transfer_System">ECTS</a>. Davon sind 15 ECTS für die Bachelor-Arbeit, 6 ECTS für Softskills (z.B. Sprachkurse und verpflichtent 2 ECTS für Teamarbeit in der Softwareentwicklung) und folgende Plicht-Kurse vorgesehen:</p> <table> <tr> <th>Lehrveranstaltung</th> <th>ECTS</th> <th>Weitere Links</th> </tr> <tr> <th colspan="3" style="background-color:#cdcdcd;">1. Semester</th> </tr> <tr> <td><a href="../gbi-klausur/">Grundbegriffe der Informatik</a></td> <td>4</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../abschlussaufgaben-programmieren/">Programmieren</a></td> <td>5</td> <td><a href="../programmieren-tutorium/">Mein Tutorium</a></td> </tr> <tr> <td>Höhere Mathematik I</td> <td>9</td> <td>&nbsp;</td> </tr> <tr> <td>Lineare Algebra I</td> <td>9</td> <td>&nbsp;</td> </tr> <tr> <th colspan="3" style="background-color:#cdcdcd;">2. Semester</th> </tr> <tr> <td><a href="../algorithmen-klausur/">Algorithmen I</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../swt-i-klausur/">Softwaretechnik I</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../ti-klausur-dt-ro/">Rechnerorganisation</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td>Höhere Mathematik II</td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td>Lineare Algebra II</td> <td>5</td> <td>&nbsp;</td> </tr> <tr> <th colspan="3" style="background-color:#cdcdcd;">3. Semester</th> </tr> <tr> <td><a href="../tgi-klausur/">Theoretische Grundlagen der Informatik</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../pse-am-kit/">Praxis der Software-Entwicklung</a> (PSE)</td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../os-klausur/">Betriebssysteme</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../ti-klausur-dt-ro/">Digitaltechnik und Entwurfsverfahren</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../wt-klausur/">Wahrscheinlichkeitstheorie und Statistik</a></td> <td>4.5</td> <td>&nbsp;</td> </tr> <tr> <th colspan="3" style="background-color:#cdcdcd;">4. Semester</th> </tr> <tr> <td><a href="../datenbanksysteme-klausur/">Datenbanksysteme</a></td> <td>4</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../rechnernetze-klausur/">Rechnernetze</a></td> <td>4</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../numerik-klausur/">Numerik</a></td> <td>4.5</td> <td>&nbsp;</td> </tr> <tr> <th colspan="3" style="background-color:#cdcdcd;">5. Semester</th> </tr> <tr> <td><a href="../algorithmen-ii-klausur/">Algorithmen II</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <td><a href="../programmierparadigmen-klausur/">Programmierparadigmen</a></td> <td>6</td> <td>&nbsp;</td> </tr> <tr> <th colspan="3" style="background-color:#cdcdcd;">6. Semester</th> </tr> <tr> <td>Bachelorarbeit</td> <td>15</td> <td>&nbsp;</td> </tr> <tr> <td><span>\(\sum\)</span></td> <td>124</td> <td>&nbsp;</td> </tr> </table> <p>Ich habe „<a href="../klausur-analysis-i-und-ii/">Analysis I+II</a>“ anstelle von „Höhere Mathematik I+II“ und „<a href="../klausur-lineare-algebra-i-ii/">Lineare Algebra und analytische Geometrie I+II</a>“ anstelle von „Lineare Algebra I+II“ gehört. Das sind die Mathematiker-Kurse.</p> <p>Wie ihr nun erkannt haben werdet, bleiben <code>$180 - 124 - 6 = 50$</code> übrig. Da ich die Mathematiker-Kurse gemacht habe (die jeweils 9 ECTS anstelle von 5 und 4 geben), bei mir sogar nur 41 ECTS. Davon muss man zwei Stammmodule für jeweils 6 ECTS machen. Dann sind es nur noch <code>$50-2 \cdot 6 = 38$</code> ECTS.</p> <p>Die Praxis der Softwareentwicklung (PSE) ist übrigens eine tolle Sache am KIT-Informatik-Studium. Dort sucht man sich aus einer vorgegebenen Auswahl an Projekten eines aus. Dieses bearbeitet man in einer Gruppe von 5 Studenten für ein halbes Jahr. Ich habe an einem Projekt des Frauenhofer Instituts gearbeitet, das sich UpToDatE (Upload automation and data entry) nannte. Mal schauen, vielleicht schreibe ich mal etwas darüber.</p> <h3>Stammmodule</h3> <ul> <li>Computergraphik</li> <li>Echtzeitsysteme</li> <li>Formale Systeme</li> <li><a href="../kogsys-klausur/">Kognitive Systeme</a></li> <li>Rechnerstrukturen</li> <li><a href="../sicherheit-klausur/">Sicherheit</a></li> <li>Softwaretechnik II</li> <li>Telematik</li> </ul> <h3>Proseminare</h3> <p>Die Informatik-Proseminare sind leider sehr schlecht organisiert. Ich habe auf GitHub ein öffentliches Repository, wo ihr hoffentlich <a href="https://github.com/MartinThoma/kit/tree/master/Informatik/Proseminare">aktuelle Informationen über Info-Proseminare</a> finden (bzw. auch eintragen) könnt.</p> <h3>Softstkills</h3> <p>Von den 6 ECTS für Softskills sind ja schon 2 verpflichtend in Teamarbeit für die Softwareentwicklung (TSE - gehört zu PSE). Das ist nur ein Kniff mit dem Modulhandbuch, weil man wohl kein Stammmodul mit 8 ECTS machen konnte / wollte, also hat man PSE mit 6 ECTS und 2 ECTS für TSE. Praktisch bedeutet PSE auch so viel Arbeit, dass 8 ECTS angebracht sind (eher sogar mehr) und man muss im Team arbeiten. Man bekommt die Punkte also nicht geschenkt, aber man muss auch nichts außerhalb von PSE dafür machen.</p> <p>Von den 4 übrigen Punkten kann man sich aus vielen interessanten <a href="http://www.hoc.kit.edu/lehrangebot.php">Kursen des HOC</a> etwas aussuchen, z.B. <a href="http://www.spz.kit.edu/">Kurse des Sprachenzentrums</a>. Diese sind deutlich besser als die Sprachkurse in der Schule. Ich habe mich für <a href="http://www.spz.kit.edu/englisch.php#List">English C1: Advanced</a> entschieden. Da ich aber auch ein Tutorium gehalten habe (was 4 ECTS und 8,67 Euro/Stunde gibt), hätte ich das nicht machen müssen. Der Kurs war aber so toll, dass ich es nicht bereue.</p> <h3>Weitere Kurse</h3> <p>Ich habe folgendes belegt:</p> <table> <tr> <td><a href="../web-engineering/">Web-Engineering</a></td> <td>4</td> </tr> <tr> <td>Algorithmen für planare Graphen</td> <td>5</td> </tr> </table> <p>SEHR viele weitere Kurse sind im <a href="http://www.informatik.kit.edu/1956.php">Modulhandbuch</a> zu finden.</p> <p>Hier ist übrigens mal ein Abhängigkeitsgraph zum KIT-Bachelor-Informatik:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/09/informatikstudium-kit-abhaengigkeitsgraph-300x294.png"><img src="../images/2013/09/informatikstudium-kit-abhaengigkeitsgraph-300x294.png" alt="Abhängigkeiten im Bachelor-Informatik Studium am KIT" width="" height="" class="size-medium wp-image-76453" /></a><p class="wp-caption-text">Abhängigkeiten im Bachelor-Informatik Studium am KIT</p></div> <p>Es ist am KIT als Informatiker übrigens sehr leicht eine HiWi-Stelle zu finden.</p> <h3>Ergänzungsfächer</h3> <p>Man kann am KIT aus einer Fülle von <s>Nebenfächern</s> Ergänzungsfächern wählen:</p> <ul> <li>Elektro- und Informtionstechnik</li> <li>Maschinenbau</li> <li>Mathematik</li> <li>Physik</li> <li>Grundlagen des Rechts</li> <li>Volkswirtschaftslehre</li> <li>Betriebswirtschaftslehre</li> <li>Operation Research</li> </ul> <p>Auf Anfrage kann man aber wohl noch weitere machen. So studiert ein Bekannter in Richtung Medizinische Bildgebungsverfahren einiges.</p> <h4>Mathematik</h4> <table> <tr> <td>Proseminar</td> <td>3</td> <td><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/presentations/Diskrete-Mathematik">Mein Vortrag</a> zum Proseminar Diskrete Mathematik</td> </tr> <tr> <td><a href="../eaz-klausur/">Einführung in die Algebra und Zahlentheorie</a></td> <td>9</td> <td>&nbsp;</td> </tr> <tr> <td>Topologie und Geometrie</td> <td>9</td> <td>&nbsp;</td> </tr> </table> <p>Man kann noch Analysis III und Funktionalanalysis / Hilberträume machen und vermutlich geht noch viel mehr, wenn man nachfragt.</p> <h3>Sonstiges</h3> <p>Das KIT hat eine 24h-Bibliothek (ja, die ist wirklich 24h offen, auch Sonntags. Meines Wissens macht die nur an Weihnachten zu), die <a href="http://atis.informatik.kit.edu/">ATIS</a> (tolle Lernräume, viele Computer, Drucker, ein Scanner), ein <a href="http://www.scc.kit.edu/">Rechenzentrum</a>.</p> <p>Der Campus ist zusammenhängend. Das, was als „Campus Nord“ bezeichnet wird ist ein Forschungsbereich. Dort werden keine Vorlesungen gehalten. Für Bachelor-Studenten ist der Campus Nord also irrelevant, außer ihr wollt da einen Job.</p> <h3>Tipps zum Studium</h3> <ul> <li>Ganz unbescheiden: <strong>Mein Blog ist toll</strong> ☺ Nein, im ernst, wenn du etwas vom Mathe-Stoff nicht verstehst, kann ich dir nur empfehlen mal rein zu schauen und vielleicht die Tags &bdquo;<a href="../tag/linear-algebra/">linear algebra</a>&ldquo; oder &bdquo;<a href="../tag/analysis/">analysis</a>&ldquo; zu durchstöbern. Ich blogge zu relativ vielen Themen, mal auf Deutsch und manchmal auf Englisch, die meistens für einen KIT-Informatik-Studenten von Interesse sind. Eventuell ist auch <a href="http://www.martin-thoma.de/uni.htm">meine kleine Linkliste</a> interessant.</li> <li><strong>Mathe ist interessant</strong>, aber wohl nicht jedermanns Sache. Ich denke ein guter Informatiker sollte auch gute Mathe-Kenntnisse haben. Noch kann ich nicht beurteilen, ob sich für mich das Besuchen der Mathe-Kurse (+Klausuren) gelohnt hat. Es war auf jeden Fall deutlich schwerer. Aber ich bin davon überzeugt, dass es sich lohnen wird.</li> <li><strong>Bleib am Ball</strong>: Gerade in Mathe - egal ob Analysis oder HM - muss man immer versuchen am Ball zu bleiben. Vorbereitung (das Kapitel im Skript lesen) und Nachbereitung (am Abend kurz aufschreiben: Was wurde gemacht? Und dann kontrollieren: Kann ich das auch?) lohnen sich. Bzw., ich habe das im 2. Semester nicht gemacht und es hat sich bei der Klausurvorbereitung gerächt.</li> <li>Die ersten Vorlesungen sind besonders wichtig. In fast allen gibt es ein gutes Skript, das auch online ist. Fast überall wird genau das Skript gemacht, nicht mehr und nicht weniger. Aber manchmal werden Dinge im <strong>Skript</strong> eher betont oder vielleicht etwas genauer erklärt/ein Beispiel mehr gemacht. Also: Skript direkt am Anfang ausdrucken und immer mitnehmen.</li> <li><strong>Drucken</strong>: Bis auf die Skripte würde ich alles in der ATIS (und nicht im SCC) drucken. Du solltest nach der O-Phase beide Accounts haben.</li> <li><strong>Übungsblätter</strong>: Es lohnt sich, die Übungsblätter ordentlich zu machen. Sie sind, neben Altklausuren, die beste Klausurvorbereitung. Also: Mache deine Lösungen kleinschrittig, eventuell mit Erklärungen die du in einem Semester nutzen kannst, schreibe sie sauber auf und mach alle. Egal wie schwer sie sind oder wie wenig Zeit du hast. Das wird - im 2. Semester - anstrengend, aber es lohnt sich. Also nicht nur auf die Punkte schauen, die du für den Übungsschein brauchst, sondern auch an die bevorstehende Klausur denken.</li> </ul> <h3>FAQ</h3> <ul> <li><strong>Frage</strong>: Ich kann nich programmieren. Ist das schlimm? <strong>Antwort</strong>: Nein! Am KIT lernt man alles von Grund auf. In &bdquo;Programmieren&ldquo; lernt man Java, in &bdquo;Betriebssysteme&ldquo; grundlegendes C, in &bdquo;PSE&ldquo; - je nach dem was man macht - C++, Java, C#, in &bdquo;SWT I&ldquo; grundlagen über paralleles Programmieren mit Java.</li> <li><strong>Frage</strong>: Wie Praxisnah ist das Studium? <strong>Antwort</strong>: Kommt darauf an, was man später machen will und was man als Vergleich nimmt. Vermutlich sind die Fachhochschulen näher an der Praxis, wenn man auf reines Programmieren hinaus will. Aber wenn ihr einfach nur im Beruf programmieren wollt, müsst ihr nicht studieren. Vielleicht macht dann eine Ausbildung mehr Sinn.</li> <li><strong>Frage</strong>: Was lernt man in der Informatik, wenn nicht Programmieren? <strong>Antwort</strong>: Vieles. Algorithmen und Datenstrukturen, wie genau ein Rechner von einzelnen Transistoren, über Schaltungen, Schaltwerke, Maschinencode und Assembler funktioniert, was theoretische Berechnungsmodelle sind, was überhaupt berechenbar ist, wie Computer lernen können, wie man mit Ungenauigkeit in Berechnungen umgeht, wie man Programme/Probleme sinnvoll strukturiert, was Sicherheit in der Informatik ist und wie man verschiedene Sicherheitsbegriffe zeigen kann...</li> <li><strong>Frage</strong>: Was ist charakteristisch für die Informatik am KIT? <strong>Antwort</strong>: Das KIT hat eine gro&szlig;e Informatik-Fakultät. Wenn man hier Informatik zu studieren beginnt, kann man sich in alle (oder zumindest viele) Richtungen weiterentwickeln. Au&szlig;erdem ist das Informatik-Studium am KIT sehr Mathematik-lastig.</li> <li><strong>Frage</strong>: Ich würde gerne XYZ lernen, aber das steht nicht im Modulhandbuch. Kann ich das trotzdem am KIT lernen? <strong>Antwort</strong>: Es gibt einen E-Mail-Verteiler für Studenten. Dort kann man einfach mal fragen, ob andere auch interesse daran haben. Au&szlig;erdem gibt es <a href="http://www.kit.edu/studieren/studentische_einrichtungen.php">Hochschulgruppen</a>. Bei über 3000 Studenten wird sich schon jemand finden, der auch XYZ machen will / es kann.</li> </ul> <h2>Karlsruhe</h2> <p>Am KIT werden immer wieder interessante Vorträge gehalten, z.B.</p> <ul> <li>Google Tech Talk: JavaScript and V8 - A functional-ish language and implementation in the mainstream</li> <li><a href="http://www.talkit.eu/talkit/index.php/thema-269.html">TalKIT</a></li> <li><a href="https://www.uni-karlsruhe.de/cos/EventList.php?cal_id=47&amp;language=de&amp;sort=time_asc&amp;from_day=1&amp;from_month=1&amp;from_year=1990">Weitere</a></li> </ul> <p>Es gibt den <a href="http://www.scienceslam-karlsruhe.de/index/science_Slam_karlsruhe/science_Slam_karlsruhe.html">Science Slam Karlsruhe</a>, <a href="http://www.physik.kit.edu/Aktuelles/Physik_am_Samstag/">Physik am Samstag</a> und <a href="http://kalender.karlsruhe.de/kalender/db/termine">sehr viele weitere Veranstaltungen</a>.</p> <p>Falls man mehr über Karlsruhe wissen will: Auch dazu gibt es einen <a href="https://de.wikipedia.org/wiki/Karlsruhe">Wikipedia-Artikel</a>.</p> <h3>Wohnungen</h3> <p>Tja, eine Wohnung zu finden ist in Karlsruhe schwer. Mit der Wohnungssuche sollte man sehr früh beginnen. Es gibt zwar <a href="http://www.studentenwerk-karlsruhe.de/de/wohnen/wohnheime_ka/">einige Wohnheime</a>, aber auch die sind voll. Und die Qualität der Wohnheime ist sehr unterschiedlich. Ich habe gehört, dass das HaDiKo und die Insterburg nicht so toll sind, aber das an der Waldhornstraße soll sehr gut sein. Es gibt neben den Wohnheimen in dieser Liste noch mindestens eine weiteres (das <a href="http://www.ev-studentinnenwohnheim.de/">evangelische Studentinnen-Wohnheim</a> in Rüpurr).</p> <p>Die zentralen Wohnungen sind meistens Altbauwohnungen. Ich habe meine über studenten-wg.de gefunden.</p> <p>Allgemein gilt jedoch: Umso früher man sucht, umso besser.</p> <p>Für einen Eindruck von Karlsruhe kann man sich meine <a href="https://www.google.com/maps/views/profile/116515806655836046525?gl=us">Photo-Spheres</a> anschauen.</p> Gedanken zur Bundestagswahl 2013 //martin-thoma.com/gedanken-zur-bundestagswahl-2013/ Fri, 06 Sep 2013 11:54:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/gedanken-zur-bundestagswahl-2013 <p>Am 22. September 2013 findet die Bundestagswahl 2013 statt.</p> <h2>Worum geht es?</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/qP6ye8R_QEA" frameborder="0" allowfullscreen=""></iframe> <h2>Parteien</h2> <p>Ich werde jeweils zwei Videos verlinken. Eines von „MrWissen2go“ und einen Wahlwerbespot der Parteien selbst. Die Parteien sind aufsteigend nach vermutlichem Ergebnis geordnet.</p> <h3>Piraten</h3> <table> <tr> <th colspan="2"><img src="../images/2013/09/Piratenpartei-logo.png" alt="Logo der Piratenpartei" width="300" height="140" class="size-full wp-image-76414" /></th> </tr> <tr> <th>Mitgliederzahl</th> <td>31.669</td> </tr> <tr> <th>Durch&shy;schnitts&shy;alter</th> <td>38,9 Jahre</td> </tr> <tr> <th>Frauen&shy;anteil</th> <td>ca. 5&ndash;15 Prozent</td> </tr> <tr> <th>Themen</th> <td> <ul> <li>Transparenz</li> <li>Bedingungsloses Grundeinkommen</li> <li>Datenschutz und Internet</li> </ul> </td> </tr> <tr> <th>Wahlprogramm</th> <td> <ul> <li><a href="https://www.piratenpartei.de/wp-content/uploads/2013/06/PP-Bund-BTW13v1.pdf">Vollständig als PDF</a> (recht gro&szlig;)</li> <li><a href="http://www.piraten-zur-wahl.de/index.php/hoerbuch/">als Hörbuch</a></li> </ul> </td> </tr> </table> <iframe width="512" height="288" src="//www.youtube.com/embed/GNE0NOhN0pU" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="//www.youtube.com/embed/d5dMwpfDCTM" frameborder="0" allowfullscreen=""></iframe> <h3>DIE LINKE.</h3> <table> <tr> <th colspan="2"><img src="../images/2013/09/die-linke.png" alt="DIE LINKE." width="250" height="56" class="size-full wp-image-76417" /></th> </tr> <tr> <th>Mitgliederzahl</th> <td>63.761</td> </tr> <tr> <th>Durch&shy;schnitts&shy;alter</th> <td>60 Jahre</td> </tr> <tr> <th>Frauen&shy;anteil</th> <td>37,7 Prozent</td> </tr> <tr> <th>Themen</th> <td> <ul> <li>10 Euro Mindeslohn</li> <li>Höhere Steuern auf hohe Einkommen</li> <li>Höhere Sozialleistungen</li> </ul> </td> </tr> <tr> <th>Wahlprogramm</th> <td> <ul> <li><a href="http://www.die-linke.de/fileadmin/download/wahlen2013/bundestagswahlprogramm/bundestagswahlprogramm2013_langfassung.pdf">Vollständig als PDF</a> (912 kB)</li> <li><a href="http://www.die-linke.de/fileadmin/download/wahlen2013/kurzfassung_audio/bundestagswahlprogramm2013_kurzfassung_weibliche_stimme.mp3">als Hörbuch</a> (6.1 MB)</li> </ul> </td> </tr> </table> <iframe width="512" height="288" src="//www.youtube.com/embed/TJzWq0O2k_Y" frameborder="0" allowfullscreen=""></iframe> <p>Ich konnte leider keinen “offiziellen” Wahlwerbespot finden. Aber der folgende Clip kommt dem am nächsten:</p> <iframe width="512" height="384" src="//www.youtube.com/embed/oUz1qPJ8NoA" frameborder="0" allowfullscreen=""></iframe> <h3>FDP</h3> <table> <tr> <th colspan="2"><img src="../images/2013/09/FDP-logo.png" alt="Logo der FDP" width="150" height="137" class="size-full wp-image-76421" /></th> </tr> <tr> <th>Mitgliederzahl</th> <td>58.675</td> </tr> <tr> <th>Durch&shy;schnitts&shy;alter</th> <td>53 Jahre</td> </tr> <tr> <th>Frauen&shy;anteil</th> <td>23,0 Prozent</td> </tr> <tr> <th>Themen</th> <td> <ul> <li>Staatsschulden abbauen ohne Steuererhöhung</li> <li>Bürgergeld</li> <li>Soli abschaffen</li> </ul> </td> </tr> <tr> <th>Wahlprogramm</th> <td><a href="http://www.fdp.de/files/408/B_rgerprogramm_A5_Online_2013-07-23.pdf">Vollständig als PDF</a></td> </tr> </table> <iframe width="512" height="288" src="//www.youtube.com/embed/UTIm_8-X4gM" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="//www.youtube.com/embed/IQQ5nREaJWs" frameborder="0" allowfullscreen=""></iframe> <h3>Grüne</h3> <table> <tr> <th colspan="2"><img src="../images/2013/09/gruenen-logo.png" alt="Logo von Bündnis 90 - die Grünen" width="180" height="108" class="size-full wp-image-76422" /></th> </tr> <tr> <th>Mitgliederzahl</th> <td>60.808</td> </tr> <tr> <th>Durch&shy;schnitts&shy;alter</th> <td>48 Jahre</td> </tr> <tr> <th>Frauen&shy;anteil</th> <td>37,8 Prozent</td> </tr> <tr> <th>Themen</th> <td> <ul> <li>Höhere Steuern auf hohe Einkommen</li> <li>Kostenlose Kita-Plätze</li> <li>8,50 Euro Mindestlohn</li> <li>Bürgerversicherung für alle</li> <li>Massentierhaltung abschaffen</li> <li>Gentechnik verhindern</li> <li>ÖPNV billiger machen</li> </ul> </td> </tr> <tr> <th>Wahlprogramm</th> <td> <ul> <li><a href="http://www.gruene.de/fileadmin/user_upload/Dokumente/Wahlprogramm/Wahlprogramm-barrierefrei.pdf">Vollständig als PDF</a></li> <li><a href="http://gruene-clips.de/content/Wahlprogramm-2013_Audio_mp3.zip">Hörbuch</a></li> </ul> </td> </tr> </table> <iframe width="512" height="288" src="//www.youtube.com/embed/LeHiHZ8m2rU" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="//www.youtube.com/embed/NwOcVbGn7Qs" frameborder="0" allowfullscreen=""></iframe> <h3>SPD</h3> <table> <tr> <th colspan="2"><img src="../images/2013/09/spd-logo.png" alt="SPD Logo" width="150" height="150" class="size-full wp-image-76423" /></th> </tr> <tr> <th>Mitgliederzahl</th> <td>472.469</td> </tr> <tr> <th>Durch&shy;schnitts&shy;alter</th> <td>59 Jahre</td> </tr> <tr> <th>Frauen&shy;anteil</th> <td>31,5 Prozent</td> </tr> <tr> <th>Themen</th> <td> <ul> <li>Höhere Steuern für höhere Einkommen</li> <li>Wahlalter auf 16 Jahre senken</li> <li>Kostenlose Kita-Plätze</li> <li>Volle Rente ab 63 Jahren für alle, die min. 45 Jahre gearbeitet haben</li> </ul> </td> </tr> <tr> <th>Wahlprogramm</th> <td><a href="http://www.spd.de/linkableblob/96686/data/20130415_regierungsprogramm_2013_2017.pdf">Vollständig als PDF</a></td> </tr> </table> <iframe width="512" height="288" src="//www.youtube.com/embed/WNkDGxaRutQ" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="//www.youtube.com/embed/ffG18Nz5cSQ" frameborder="0" allowfullscreen=""></iframe> <h3>CDU / CSU</h3> <table> <tr> <th colspan="2"><img src="../images/2013/09/cdu-partei.png" alt="CDU - Partei" width="250" height="74" class="size-full wp-image-76418" /></th> </tr> <tr> <th>Mitgliederzahl</th> <td>469.575</td> </tr> <tr> <th>Durch&shy;schnitts&shy;alter</th> <td>59 Jahre</td> </tr> <tr> <th>Frauen&shy;anteil</th> <td>25,6 Prozent</td> </tr> <tr> <th>Themen</th> <td> <ul> <li>konservativ (im Gro&szlig;en und Ganzen soll sich nichts ändern)</li> <li>mehr Kameraüberwachung</li> <li>Mieten sollen im öffentlichen Raum nicht weiter ansteigen</li> </ul> </td> </tr> <tr> <th>Wahlprogramm</th> <td> <ul> <li><a href="http://www.cdu.de/sites/default/files/media/dokumente/cdu_regierungsprogramm_2013-2017.pdf">Vollständig als PDF</a> (683.47 kB)</li> <li><a href="http://www.cdu.de/sites/default/files/media/dokumente/bilanz-btw13.pdf">als Hörbuch</a> (1.44 MB)</li> </ul> </td> </tr> </table> <iframe width="512" height="384" src="//www.youtube.com/embed/99zpMPcgnHc" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="//www.youtube.com/embed/Mk06yfbXQYg" frameborder="0" allowfullscreen=""></iframe> <h2>Koalitionsmöglichkeiten</h2> <div style="width: 468px" class="wp-caption aligncenter"><a href="../images/2013/09/koalitionsrechner.png"><img src="../images/2013/09/koalitionsrechner.png" alt="Koalitionsrechner - Ergebnis" width="" height="" class="size-full wp-image-76427" /></a><p class="wp-caption-text">Koalitionsrechner - Ergebnis</p></div> <p>Die Parteien haben viele aussagen über Koalitionen nach der Bundestagswahl gemacht:</p> <ul> <li>Für CDU/CSU kommt die FDP und die SPD in Frage. (<a href="http://www.spiegel.de/politik/deutschland/kanzlerin-spricht-ueber-grosse-koalition-merkel-veraergert-fdp-a-917219.html">Quelle</a>)</li> <li>Die FDP will nur mit der Union eine Koalition. (<a href="http://www.n-tv.de/ticker/Westerwelle-schliesst-erneut-Koalition-mit-SPD-und-Gruenen-aus-article11278791.html">Quelle</a>)</li> <li>Rot-Rot-Grün wird es nicht geben. (<a href="http://www.sueddeutsche.de/politik/rot-rot-gruen-linke-phantasien-vor-der-bundestagswahl-1.1755513">Quelle</a>, siehe auch im Wahlprogramm der Grünen: &bdquo;Die Linke steht abseits des grünen Wandels.&ldquo;)</li> <li>Die SPD will eigentlich nur mit den Grünen. (<a href="http://www.n24.de/n24/Nachrichten/Politik/d/3468674/steinbrueck-oeffnet-tuerspalt-fuer-die-linke.html">Quelle</a>)</li> </ul> <p>Nun kann man Umfrageergebnisse betrachten:</p> <div style="width: 856px" class="wp-caption aligncenter"><a href="../images/2013/09/umfragen-bundestagswahl-2013.png"><img src="../images/2013/09/umfragen-bundestagswahl-2013.png" alt="Umfrageergebnisse zur Bundestagswahl 2013" width="" height="" class="size-full wp-image-76428" /></a><p class="wp-caption-text">Umfrageergebnisse zur Bundestagswahl 2013<br />Quelle: <a href="http://www.wahlrecht.de/umfragen/index.htm">wahlrecht.de</a></p></div> <p>Damit steht fest:</p> <ul> <li>CDU / CSU bleibt in der Regierung.</li> <li>Wenn die FDP die 5%-Hürde schafft, gibt es wieder Schwarz-Gelb.</li> <li>Sonst wirds vielleicht interessant, aber vermutlich Schwarz-Rot</li> </ul> <h2>Themen</h2> <p>Ich finde es interessant, welche Themen für die Parteien wichtig sind und welche in der Öffentlichkeit häufig diskutiert werden. Im folgenden mal einige Themen, die meiner Meinung nach wichtig sind.</p> <h3>Sozialer Ausgleich</h3> <p>Ich denke, dass in Deutschland die viel zitierte „Schere zwischen Arm und Reich“ zu groß wird. Zu dem Thema gibt es in den Wiki-Artikeln <a href="https://de.wikipedia.org/wiki/Einkommensverteilung_in_Deutschland">Einkommensverteilung in Deutschland</a> und <a href="https://de.wikipedia.org/wiki/Verm%C3%B6gensverteilung_in_Deutschland">Vermögensverteilung in Deutschland</a> viele Informationen, z.B.:</p> <ul> <li>2008 betrug nach Zahlen des DIW das mittlere verfügbare Einkommen 1.252 Euro</li> <li>die ärmsten 50% haben 1,4% des Vermögens in Deutschland</li> <li>die Top 0,1 % haben 22,5% des Vermögens in Deutschland</li> <li>die Top 10% haben 66,6% des Vermögens in Deutschland</li> <li>5 Mio. verdienen weniger als 8,50 Euro pro Stunde (<a href="http://www.suedkurier.de/nachrichten/politik/schwerpunkt/Hintergrund-5-Mio-verdienen-weniger-als-8-50-Euro;art10035,5197727">Quelle</a>)</li> <li>Im Jahr 2011 sind an mehr als 1,21 Millionen Bedarfsgemeinschaften mit Aufstockern durchschnittlich 737 Euro je Monat gezahlt worden. (<a href="http://www.tagesschau.de/inland/hartziv222.html">Quelle</a>)</li> </ul> <p>Es ist sehr einfach, was dagegen hilft:</p> <ul> <li>Höhere Steuern auf höhere Einkommen</li> <li>Mindestlohn</li> <li>Höhere Sozialleistungen für Arme</li> <li>Höhe Erbschaftsvermögen (um eine konkrete Zahl zu nennen: &gt; 10,000,000 Euro) müssen stark mit Erbschaftssteuer eingeschränkt werden. Davor darf es keine &bdquo;Steuerflucht&ldquo; geben. (Existiert dieses Problem?)</li> </ul> <p>Ich bin außerdem davon überzeugt, dass viele Menschen, die eigentlich Anspruch auf Sozialleistungen hätten, diesen nicht in Anspruch nehmen. Zum einen, weil sie es nicht wollen (<a href="http://www.wdr2.de/aktuell/hartzvier122.html">Quelle</a>), zum anderen aber vermutlich auch, weil sie nicht wissen, dass sie Anspruch haben.</p> <p>Hier mal ein paar Leistungen, die es gibt:</p> <ul> <li><a href="https://de.wikipedia.org/wiki/Arbeitslosengeld">Arbeitslosengeld</a></li> <li><a href="https://de.wikipedia.org/wiki/Arbeitslosengeld_II">Arbeitslosengeld II</a></li> <li><a href="https://de.wikipedia.org/wiki/Baf%C3%B6g">BAföG</a></li> <li>Hartz IV</li> <li><a href="https://de.wikipedia.org/wiki/Kinderzuschlag">Kinderzulage</a></li> <li><a href="https://de.wikipedia.org/wiki/Kindergeld_(Deutschland)">Kindergeld</a></li> <li><a href="https://de.wikipedia.org/wiki/Kinderkrankengeld">Kinderkrankengeld</a></li> <li><a href="https://de.wikipedia.org/wiki/Elterngeld_(Deutschland)">Elterngeld</a></li> <li><a href="https://de.wikipedia.org/wiki/%C3%9Cbergangsgeld">Übergangsgeld</a></li> <li><a href="https://de.wikipedia.org/wiki/Wohngeld">Wohngeld</a></li> <li><a href="https://de.wikipedia.org/wiki/Wohnungshilfe">Wohnungshilfe</a></li> </ul> <p>In der <a href="https://de.wikipedia.org/wiki/Kategorie:Sozialleistung_(Deutschland)">Kategorie:Sozialleistung (Deutschland)</a> findet man noch viel mehr.</p> <h3>Eurokrise</h3> <p>Die <a href="https://de.wikipedia.org/wiki/Eurokrise">Eurokrise</a> muss beendet werden. Wichtige Zahlen dazu sind:</p> <ul> <li>Die Jugendarbeitslosigkeit in Spanien betrug 2012 ca. 24,9%.</li> <li>Griechenland: Arbeitslosigkeit bei Menschen mit Hochschulbildung unter 24 Jahren: 28,8% - in Deutschland 12,8%</li> <li>In Griechenland betrug die Arbeitslosigkeit 2011 ca. 17,6%</li> <li>Die <a href="https://de.wikipedia.org/wiki/Staatsverschuldung#Staatsverschuldung_in_entwickelten_L.C3.A4ndern">Staatverschuldung</a> ist katastrophal - egal ob man Deutschland, Frankreich, Spanien, Griechenland oder Italien anschaut.</li> </ul> <p>Hier kann man nicht davon ausgehen, dass irgendeine Partei eine belegbar gute Lösung vorbringt. Wie auch? Das Problem gab es noch nie. Aber die Frage nach dem, was man zu tun gedenkt ist doch interessant:</p> <ul> <li>CDU / CSU: <ul> <li>Für: Sparma&szlig;nahmen, Schuldenbremse, <a href="https://de.wikipedia.org/wiki/Stabilit%C3%A4ts-_und_Wachstumspakt">Stabilitätspakt</a>, Europäische Bankenunion</li> <li>Gegen: Eurobonds</li> </ul> <li>SPD: <ul> <li>Für: Finanztransaktionssteuer</li> </ul> </li> <li>DIE LINKE.: <ul> <li>Für: Einmalige Abgabe von 10% auf Vermögen zur Schuldentilgung bei einem Freibetrag von 1.000.000 Euro auf Privatvermögen und 2.000.000 Euro auf Betriebsvermögen; Finanztransaktionssteuer</li> </ul> </li> <li>Piraten: <ul> <li>Für: Finanztransaktionssteuer; Schuldenschnitte</li> </ul> </li> <li>Grüne: <ul> <li>Für: Vermögensabgabe (vergleichbar mit LINKE)</li> </ul> </li> Das ist selbstverständlich keine vollständige Liste. Wenn es einen wirklich interessiert, sollte man das Wahlprogramm der Parteien danach durchsuchen. <h3>Korruption und Transparenz</h3> Korruption kann dazu führen, dass Entscheidungen getroffen werden, die für den Staat nicht optimal sind. Dazu sollte Abgeordnetenbestechung zuerst einmal illegal sein, also ein &bdquo;Anti-Korruptionsgesetz&ldquo; eingeführt werden. Dagegen wehren sich aber CDU/CSU und FDP sehr. Es gab auch schon eine <a href="http://www.abgeordnetenwatch.de/schaerfere_regeln_gegen_abgeordnetenbestechung-605-525.html">Abstimmung Schärfere Regeln gegen Abgeordnetenbestechung</a> - kontrolliert doch selbst, wie eure Abgeordneten abgestimmt haben. Au&szlig;erdem führt der Verdacht auf bestechliche Politiker zu weiterer Politikverdrossenheit. Siehe zu Abgeordnetenbestechung: <ul> <li><a href="http://beta.abgeordnetenwatch.de/blog/2013-06-07/blockade-bei-abgeordnetenbestechung-ausschussvorsitzender-kauder-uebt-scharfe-kritik">Blockade bei Abgeordnetenbestechung</a></li> <li><a href="http://beta.abgeordnetenwatch.de/blog/2013-08-14/abgeordnetenbestechung-mit-wem-will-seehofer-eigentlich-eine-gesetzesverschaerfung">Abgeordnetenbestechung: Mit wem will Seehofer eigentlich eine Gesetzesverschärfung durchsetzen?</a></li> <li><a href="http://beta.abgeordnetenwatch.de/blog/2013-06-26/ueberraschung-bundestag-soll-doch-noch-ueber-abgeordnetenbestechung-abstimmen">Überraschung: Bundestag soll doch noch über Abgeordnetenbestechung abstimmen</a></li> </ul> <h3>Energiewende</h3> Die Versorgung mit Energie ist ein essentieller bestandteil der öffentlichen Infrastruktur. Sei es in Form von elektrischer Energie für Haushalte und Firmen, in Form von Wärme oder in Form von Mobilität. Dabei wäre es schön, das Problem nachhaltig zu lösen. Momentan geschieht dies in Form von <a href="https://de.wikipedia.org/wiki/Liste_von_Onshore-Windparks_in_Deutschland">On</a>- und <a href="https://de.wikipedia.org/wiki/Liste_der_Offshore-Windparks">Offshore Windkraftparks</a> sowie im <a href="https://de.wikipedia.org/wiki/Netzausbau">Netzausbau</a>. Das <a href="https://de.wikipedia.org/wiki/Erneuerbare-Energien-Gesetz">Erneuerbare-Energien-Gesetz</a> (EEG) soll dabei helfen und regelt die sog. <a href="https://de.wikipedia.org/wiki/Einspeiseverg%C3%BCtung">Einspeisevergütung</a>. <h3>Steuern</h3> Im Bezug auf Steuern sehe ich zwei gro&szlig;e Probleme: <ol> <li>Konzerne spielen Länder gegeneinander aus</li> <li>Steuern sind in Deutschland kompliziert</li> </ol> Das Konzerne Länder gegeneinander ausspielen, sieht man an Google (<a href="http://www.googlewatchblog.de/2012/11/frankreich-milliarden-euro-steuernachzahlung/">Quelle</a>). Versteht mich jetzt nicht falsch, ich finde Google super. Aber jedes Unternehmen wird, wenn es ihm auf legale Art möglich ist, versuchen Kosten (also auch Steuern) so niedrig wie möglich zu halten. Also sollte man sich doch innerhalb der Euro-Zone auf ein gemeinsames Steuersystem einigen können, oder? Au&szlig;erdem scheint es mir in Deutschland zu viele Steuern/Abgaben zu geben und diese auch zu kompliziert zu sein Sinnvoll finde ich <ul> <li>Erbschaftssteuer: Sie sorgt dafür, dass sich Reichtum weniger stark anhäuft.</li> <li><span class="hint" title="Mehrwertsteuer">Umsatzsteuer</span>: Sie stellt einen einfachen Weg dar, wie der Staat an Geld kommt. Sie betrifft alle gleichmä&szlig;ig. Ich finde es nicht sinnvoll, hier zwischen verschiedenen Klassen (Lebensmittel, Luxusgüter) zu unterscheiden. Wenn Lebensmittel mehr kosten würden, würde man ihren Wert vielleicht mehr schätzen. </li> <li>Einkommensteuer: Auch mit der Lohnsteuer bekommt der Staat viel Geld. Aber im Gegensatz zur Umsatzsteuer kann man hier Leute, die viel Verdienen stärker belasten.</li> <li>Energiesteuern: Durch Energiesteuern kann man Anreize schaffen, sparsame Geräte / Infrastruktur zu entwickeln. Dies sollte für die Bürger auf lange Sicht von Vorteil sein.</li> <li><span class="hint" title="Tabaksteuer">Rauschmittelsteuern</span>: Eigentlich sollten Menschen nicht rauchen und saufen. Also sollten diese Produkte - obwohl sie eventuell billig in der Herstellung sind - teuer verkauft werden. Die Steuer sollte süchtigen dazu dienen, von ihrer Sucht frei zu kommen bzw. in die Suchtprävention gesteckt werden.</li> <li>Grundsteuer: Durch eine hohe Grundsteuer nutzt vermutlich derjenige, der am meisten damit verdienen kann, das Grundstück. Sie kann also eine gute Verteilung dieser knappen Ressource ermöglichen.</li> </ul> Steuern/Abgaben die ich nicht verstehe, sind: <ul> <li><a href="https://de.wikipedia.org/wiki/Solidarit%C3%A4tszuschlag">Solidaritätszuschlag</a></li> <li><a href="https://de.wikipedia.org/wiki/Kirchensteuer_(Deutschland)">Kirchensteuer</a>: Das sollte die Kirche selbst machen!</li> <li>Arbeitslosenversicherung: Sollte durch Umsatz- und Einkommenssteuer gedeckt werden. Grundstätzlich denke ich sollte hier jeder gleich versichert sein. Wenn jemand mehr als grundlegende Leistungen will, soll er das Privat machen. Aber eine gewisse Grundsicherung soll jeder bekommen.</li> <li>Krankenversicherung: Siehe Arbeitslosenversicherung</li> <li>Pflegeversicherung: Siehe Arbeitslosenversicherung</li> <li>Tabak, Alkopop, Schaumwein: Sollte eine &bdquo;Rauschmittelsteuer&ldquo; sein</li> <li><a href="https://de.wikipedia.org/wiki/Grunderwerbsteuer_(Deutschland)">Grunderwerbssteuer</a>: Warum wird Grunderwerb extra gezählt? Warum nicht einfach nur Umsatzsteuer?</li> <li><a href="https://de.wikipedia.org/wiki/Zinsabschlag">Kapitalertragsteuer</a>: Warum ist das nicht einfach Einkommenssteuer?</li> <li>Versicherungsteuer, <a href="https://de.wikipedia.org/wiki/Kraftfahrzeugsteuer">Kraftfahrzeugsteuer</a>: Siehe Grunderwerbsteuer</li> <li>Stromsteuer: Inwiefern unterscheided sie sich von der Energiesteuer?</li> </ul> Ganz allgemein sollte es wenig S1teuern geben. Die Steuer die es gibt, sollten einfach zu verstehen und zu berechnen sein. Au&szlig;erdem sollte es eine vollständige, aktuelle, frei verfügbare Liste der Steuern sowie der Berechnung selbiger geben. Ich wei&szlig; nicht, wie die Lohnsteuer berechnet wird. Sinnvoll würde ich folgende Berechnung finden: <ul> <li>Am Ende eines Jahres wird das Einkommen (Lohn, Kapitalerträge) berechnet.</li> <li>Sei dieses Gesamteinkommen `$x$` (in Euro): <ul> <li>`$x \leq 12.000$`: Keine Steuer</li> <li>`$x \leq 24.000$`: 15% Steuer. Die zu bezahlende Steuer ist also `$(x - 12.000) \cdot \frac{15}{100}$`</li> <li>`$x \leq 36.000$`: 20% Steuer. Die zu bezahlende Steuer ist also `$(36.000 - 12.000) \cdot \frac{15}{100} + (x-24.000) \cdot \frac{20}{100}$`</li> <li>...</li> <li>`$x &gt; 120.000$`: 50% Steuer. Die zu bezahlende Steuer ist also `$(36.000 - 12.000) \cdot \frac{15}{100} + (36.000-24.000) \cdot \frac{20}{100} + \dots + (x-120.000) \cdot \frac{50}{100}$`</li> </ul> </li> </ul> Bitte hängt euch nicht an den Zahlen auf. Das sollte nur das System veranschaulichen. Mit diesem System wäre es ganz einfach zu berechnen, wer wieviel zahlen muss. Damit kann es auch nicht passieren, dass jemand trotz höherem Einkommen weniger Geld hat. Hier mal eine Grafik über das Steueraufkommen in Deutschland: <div style="width: 810px" class="wp-caption aligncenter"><a href="../images/2013/09/steueraufkommen-deutschland.png"><img src="../images/2013/09/steueraufkommen-deutschland.png" alt="Steueraufkommen in Deutschland (Stand: 2008)" width="" height="" class="size-full wp-image-76434" /></a><p class="wp-caption-text">Steueraufkommen in Deutschland (Stand: 2008)</p></div> Es gibt noch den Ansatz der &bdquo;<a href="https://de.wikipedia.org/wiki/Flat_Tax">Flat Tax</a>&ldquo;, die Steuern einfacher machen soll. Ob das sinnvoll ist, kann ich nicht sagen. Aber eine Vereinfachung verbunden mit einer Europäischen Vereinheitlichung könnte Firmen entlasten und Steuerschlupflöcher schlie&szlig;en. <h3>Bürgerrechte</h3> Im <a href="https://de.wikipedia.org/wiki/%C3%9Cberwachungs-_und_Spionageaff%C3%A4re_2013">Spähskandal</a> (NSA, Prism, Tempora, Xkeyscore, ...) hat die CDU/CSU bisher nichts gemacht, um für Aufklärung und Beendigung der illegalen Praktiken zu sorgen. In einigen anderen Berechen wurden jedoch kritische Gesetze/Projekte/Aussagen umgesetzt/gestartet/gemacht: <ul> <li>Verkauf von Meldedaten, manchmal auch &bdquo;Bestandsdatenauskunft&ldquo; genannt (<a href="http://beta.abgeordnetenwatch.de/2013/02/27/erfolgreicher-protest-verbraucherfeindliches-meldegesetz-beerdigt">Quelle</a>)</li> <li>Mehr <a href="https://de.wikipedia.org/wiki/Video%C3%BCberwachung">Videoüberwachung</a></li> <li><a href="http://www.spiegel.de/netzwelt/web/sascha-lobo-ueber-friedrichs-realitaetsferne-sicht-auf-die-nsa-affaere-a-920041.html">Friedrich nimmt NSA in Schutz</a></li> <li>Vorratsdatenspeicherung (siehe <a href="http://www.abgeordnetenwatch.de/vorratsdatenspeicherung-636-140----abst_ja.html">Abstimmung</a>, <a href="http://www.abgeordnetenwatch.de/eu_richtlinie_zur_vorratsdatenspeicherung-136-131.html">EU-Richtlinie</a>)</li> </ul> Aber auch die SPD scheint in dem NSA-Skandal nicht ganz unbeteiligt zu sein (<a href="http://www.tagesschau.de/inland/bndnsa100.html">Quelle</a>). Auch die Vorratsdatenspeicherung haben sie mit beschlossen. Die Grünen und Piraten sind gegen Videoüberwachung, wollen das Fernmeldegeheimnis zu einem Kommunikations- und Mediennutzungsgeheimnis ausweiten, gegen die Bestandsdatenauskunft vorgehen und Vorratsdatenspeicherung verhindern. <h3>Kleine Themen</h3> Mit folgenden Themen scheinen die Parteien ihren Wahlkampf zu betreiben. Obwohl sie für einzelne Leute sehr wichtig sein mögen, glaube ich das sie im gro&szlig;en und ganzen zu vernachlässigen sind. Verglichen mit den obigen Themen betreffen die folgenden Themen nur wenige Leute. Einiges davon habe ich aus dem <a href="http://www.wahl-o-mat.de">Wahl-o-mat</a>: <ul> <li>Adoptionsrecht / Gleichstellung für Homosexuelle</li> <li>Betreuungsgeld</li> <li>Syrien-Krise</li> <li>Generelles Tempolimit auf Autobahnen</li> <li>NATO-Austritt Deutschlands; Rüstungsexporte; Militärische Beteiligungen Deutschlands</li> <li>Aufnahme von mehr Flüchtigen</li> <li>Einwanderung</li> <li>Lohnersatzleistungen bei Pflege von Angehörigen</li> <li>Frauenquote in Aufsichtsräten</li> <li>Renteneintrittsalter</li> <li>Ehegattensplitting</li> <li>Autobahn-Maut für Ausländer</li> </ul> <h2>Abschlie&szlig;ende Worte</h2> Dieser Artikel stellt nur eine kurze Zusammenfassung von Gedanken dar, die mir wichtig oder interessant zu sein scheinen. Bitte denkt über die Themen nach und überlegt euch: <ul> <li>Bin ich mit der Politik der letzten 4 Jahre zufrieden?</li> <li>Was ist mir wichtig?</li> </ul> Wenn man nur auf die grobe Ausrichtung der Parteien betrachtet, kann man eventuell sagen: <ul> <li>Wenn man Grundsätzlich mit der Politik der letzten Jahre zufrieden ist, sollte man CDU/CSU wählen.</li> <li>Wenn man Wert auf Transparenz legt, und will das Internetkompetenz in das Parlament kommt, sollte man die Piraten wählen.</li> <li>Wenn man auf Umweltschutz, neue (aber nicht radikale) Ideen, wert legt, sollte man die Grünen wählen</li> <li>Wenn man extreme Änderungen im sozialen Bereich will, sollte man DIE LINKE wählen.</li> <li>Wenn man CDU/CSU und FDP wieder sehen will, und will das auf Datenschutz-Aspekte mehr wert gelegt wird, sollte man FDP wählen.</li> <li>SPD: Hmm ... wenn man das gleiche in Rot will, was man schon kennt? Ich kann keinen wirklichen Themenschwerpunkt finden, in dem sich die SPD stark von der CDU/CSU abhebt.</li> </ul> Wenn es euch irgendwie kümmert, was in Deutschland passiert, solltet ihr wählen gehen. <h2>Links</h2> <ul> <li><a href="http://www.youtube.com/watch?v=X9Xhlz4uEmc">Aussagelose Wahlslogans</a></li> </ul> </li></ul> Gauß'sche Zahlen und verwandte Ringe //martin-thoma.com/gaussche-zahlen-und-verwandte-ringe/ Wed, 04 Sep 2013 09:16:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/gaussche-zahlen-und-verwandte-ringe <p>Sei <code>$\mathbb{Z}[\sqrt{z}]$</code> mit <code>$z \in \mathbb{Z}$</code> der kleinste Ring, der <code>$\mathbb{Z}$</code> und <code>$\sqrt{z}$</code> enthält. Sei <code>$A := \{a + b \sqrt{z} | a, b \in \mathbb{Z}\}$</code>.</p> <p><strong>Behauptung</strong>: <code>$\mathbb{Z}[\sqrt{z}] = A$</code> <strong>Beweis</strong>: z.Z.: <code>$\mathbb{Z}[\sqrt{z}] \subseteq A$</code> und <code>$\mathbb{Z}[\sqrt{z}] \supseteq A$</code></p> <p>Zuerst zeige ich <code>$\mathbb{Z}[\sqrt{z}] \supseteq A$</code>:</p> <ul> <li>`$\mathbb{Z}[\sqrt{z}]$` enthält `$\mathbb{Z} \Rightarrow \{a \in \mathbb{Z}\} \subseteq \mathbb{Z}[\sqrt{z}]$`</li> <li>`$\mathbb{Z}[\sqrt{z}]$` enthält `$\sqrt{z} \Rightarrow \{\sqrt{z}\} \subseteq \mathbb{Z}[\sqrt{z}]$`</li> <li>`$\mathbb{Z}[\sqrt{z}]$` ist ein Ring, also ist `$(\mathbb{Z}[\sqrt{z}], +)$` eine abelsche Gruppe.</li> <li>`$\Rightarrow A \subseteq \mathbb{Z}[\sqrt{z}]$`</li> </ul> <p>Nun <code>$\mathbb{Z}[\sqrt{z}] \subseteq A$</code>:</p> <ul> <li>`$(A, +) \leq (\mathbb{R}, +)$`, denn (UG-Kriterium) <ul> <li>`$0 = 0 + 0 \sqrt{z} \in A \Rightarrow A \neq \emptyset$`</li> <li>`$\forall (a+b \sqrt{z}), (c + d \sqrt{z}) \in A:$` `$(a+b\sqrt{z}) - (c+d\sqrt{z}) = \underbrace{(a-c)}_{\in \mathbb{Z}} + \underbrace{(b-d)}_{\in \mathbb{Z}} \sqrt{z} \in A$`</li> </ul> </li> <li>`$(A, +)$` ist abelsch, da `$(\mathbb{R}, +)$` abelsch ist</li> <li>`$(A, \cdot)$` ist Untermonoid von `$(\mathbb{R}, \cdot)$`, denn <ul> <li>`$1 = 1 + 0 \sqrt{z} \in A$`</li> <li>`$\forall (a+b \sqrt{z}), (c + d \sqrt{z}) \in A:$` `$(a+b\sqrt{z}) \cdot (c+ d\sqrt{z}) = \underbrace{(ac + z bd)}_{\in \mathbb{Z}} + \underbrace{(ad + bc)}_{\in \mathbb{Z}} \sqrt{z} \in A$`</li> </ul> </li> <li>Distributivgesetze: Vererben sich aus `$(\mathbb{R}, \cdot)$`</li> <li>`$\Rightarrow \mathbb{Z}[\sqrt{z}] \subseteq A$`</li> </ul> <p><code>$\Rightarrow \mathbb{Z}[\sqrt{z}] = A \blacksquare$</code></p> How to solve linear congruence equations //martin-thoma.com/solve-linear-congruence-equations/ Sun, 01 Sep 2013 17:43:49 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/solve-linear-congruence-equations <p>When you have a system of linear congruences like:</p> <p><code> $$ \begin{align} x &amp;\equiv 4 \mod 19\\ x &amp;\equiv 12 \mod 37\\ x &amp;\equiv 14 \mod 43 \end{align} $$</code></p> <p>you can solve it quite easily. Johannes Schickling has written a very nice <a href="http://schickling.github.io/algorithms/#/chinese-remainder-theorem">JavaScript Application</a> that applies the following algorithm online. I’ve used his source code to write the following Python code.</p> <h2>Pseudocode</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/09/SolveLinearCongruences.png"><img src="../images/2013/09/SolveLinearCongruences.png" alt="Solve a system of linear congruences" width="" height="" class="size-full wp-image-76382" /></a><p class="wp-caption-text">Solve a system of linear congruences</p></div> <h2>Python</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">ExtendedEuclideanAlgorithm</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;</span> <span class="sd"> Calculates gcd(a,b) and a linear combination such that</span> <span class="sd"> gcd(a,b) = a*x + b*y</span> <span class="sd"> As a side effect:</span> <span class="sd"> If gcd(a,b) = 1 = a*x + b*y</span> <span class="sd"> Then x is multiplicative inverse of a modulo b.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="n">aO</span><span class="p">,</span> <span class="n">bO</span> <span class="o">=</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="n">x</span><span class="o">=</span><span class="n">lasty</span><span class="o">=</span><span class="mi">0</span> <span class="n">y</span><span class="o">=</span><span class="n">lastx</span><span class="o">=</span><span class="mi">1</span> <span class="k">while</span> <span class="p">(</span><span class="n">b</span><span class="o">!=</span><span class="mi">0</span><span class="p">):</span> <span class="n">q</span><span class="o">=</span> <span class="n">a</span><span class="o">/</span><span class="n">b</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="n">b</span><span class="p">,</span> <span class="n">a</span><span class="o">%</span><span class="n">b</span> <span class="n">x</span><span class="p">,</span> <span class="n">lastx</span> <span class="o">=</span> <span class="n">lastx</span><span class="o">-</span><span class="n">q</span><span class="o">*</span><span class="n">x</span><span class="p">,</span> <span class="n">x</span> <span class="n">y</span><span class="p">,</span> <span class="n">lasty</span> <span class="o">=</span> <span class="n">lasty</span><span class="o">-</span><span class="n">q</span><span class="o">*</span><span class="n">y</span><span class="p">,</span> <span class="n">y</span> <span class="k">return</span> <span class="p">{</span> <span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="n">lastx</span><span class="p">,</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="n">lasty</span><span class="p">,</span> <span class="s">&quot;gcd&quot;</span><span class="p">:</span> <span class="n">aO</span> <span class="o">*</span> <span class="n">lastx</span> <span class="o">+</span> <span class="n">bO</span> <span class="o">*</span> <span class="n">lasty</span> <span class="p">}</span> <span class="k">def</span> <span class="nf">solveLinearCongruenceEquations</span><span class="p">(</span><span class="n">rests</span><span class="p">,</span> <span class="n">modulos</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;</span> <span class="sd"> Solve a system of linear congruences.</span> <span class="sd"> &gt;&gt;&gt; solveLinearCongruenceEquations([4, 12, 14], [19, 37, 43])</span> <span class="sd"> {&#39;congruence class&#39;: 22804, &#39;modulo&#39;: 30229}</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="k">assert</span> <span class="nb">len</span><span class="p">(</span><span class="n">rests</span><span class="p">)</span> <span class="o">==</span> <span class="nb">len</span><span class="p">(</span><span class="n">modulos</span><span class="p">)</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">M</span> <span class="o">=</span> <span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">*</span><span class="n">y</span><span class="p">,</span> <span class="n">modulos</span><span class="p">)</span> <span class="k">for</span> <span class="n">mi</span><span class="p">,</span> <span class="n">resti</span> <span class="ow">in</span> <span class="nb">zip</span><span class="p">(</span><span class="n">modulos</span><span class="p">,</span> <span class="n">rests</span><span class="p">):</span> <span class="n">Mi</span> <span class="o">=</span> <span class="n">M</span> <span class="o">/</span> <span class="n">mi</span> <span class="n">s</span> <span class="o">=</span> <span class="n">ExtendedEuclideanAlgorithm</span><span class="p">(</span><span class="n">Mi</span><span class="p">,</span> <span class="n">mi</span><span class="p">)[</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">e</span> <span class="o">=</span> <span class="n">s</span> <span class="o">*</span> <span class="n">Mi</span> <span class="n">x</span> <span class="o">+=</span> <span class="n">resti</span> <span class="o">*</span> <span class="n">e</span> <span class="k">return</span> <span class="p">{</span><span class="s">&quot;congruence class&quot;</span><span class="p">:</span> <span class="p">((</span><span class="n">x</span> <span class="o">%</span> <span class="n">M</span><span class="p">)</span> <span class="o">+</span> <span class="n">M</span><span class="p">)</span> <span class="o">%</span> <span class="n">M</span><span class="p">,</span> <span class="s">&quot;modulo&quot;</span><span class="p">:</span> <span class="n">M</span><span class="p">}</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">doctest</span> <span class="n">doctest</span><span class="o">.</span><span class="n">testmod</span><span class="p">()</span></code></pre></div> <h2>Links</h2> <ul> <li><a href="http://schickling.github.io/algorithms/#/chinese-remainder-theorem">Try it online</a></li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/SolveLinearCongruences">Sources</a></li> </ul> How to calculate the Legendre symbol //martin-thoma.com/calculate-legendre-symbol/ Sun, 01 Sep 2013 13:05:46 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/calculate-legendre-symbol <h2>Pseudocode</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/09/Calculate-Legendre.png"><img src="../images/2013/09/Calculate-Legendre.png" alt="Pseudocode: Calculate Legendre symbol" width="" height="" class="size-full wp-image-76379" /></a><p class="wp-caption-text">Pseudocode: Calculate Legendre symbol</p></div> <h2>Python</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">isPrime</span><span class="p">(</span><span class="n">a</span><span class="p">):</span> <span class="k">return</span> <span class="nb">all</span><span class="p">(</span><span class="n">a</span> <span class="o">%</span> <span class="n">i</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">a</span><span class="p">))</span> <span class="c"># http://stackoverflow.com/a/14793082/562769</span> <span class="k">def</span> <span class="nf">factorize</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">factors</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">p</span> <span class="o">=</span> <span class="mi">2</span> <span class="k">while</span> <span class="bp">True</span><span class="p">:</span> <span class="k">while</span><span class="p">(</span><span class="n">n</span> <span class="o">%</span> <span class="n">p</span> <span class="o">==</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">n</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">):</span> <span class="c">#while we can divide by smaller number, do so</span> <span class="n">factors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">p</span><span class="p">)</span> <span class="n">n</span> <span class="o">=</span> <span class="n">n</span> <span class="o">/</span> <span class="n">p</span> <span class="n">p</span> <span class="o">+=</span> <span class="mi">1</span> <span class="c">#p is not necessary prime, but n%p == 0 only for prime numbers</span> <span class="k">if</span> <span class="n">p</span> <span class="o">&gt;</span> <span class="n">n</span> <span class="o">/</span> <span class="n">p</span><span class="p">:</span> <span class="k">break</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;</span> <span class="mi">1</span><span class="p">:</span> <span class="n">factors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="k">return</span> <span class="n">factors</span> <span class="k">def</span> <span class="nf">calculateLegendre</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">p</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;</span> <span class="sd"> Calculate the legendre symbol (a, p) with p is prime.</span> <span class="sd"> The result is either -1, 0 or 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(3, 29)</span> <span class="sd"> -1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(111, 41) # Beispiel aus dem Skript, S. 114</span> <span class="sd"> -1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(113, 41) # Beispiel aus dem Skript, S. 114</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(2, 31)</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(5, 31)</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(150, 1009) # http://math.stackexchange.com/q/221223/6876</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(25, 1009) # http://math.stackexchange.com/q/221223/6876</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(2, 1009) # http://math.stackexchange.com/q/221223/6876</span> <span class="sd"> 1</span> <span class="sd"> &gt;&gt;&gt; calculateLegendre(3, 1009) # http://math.stackexchange.com/q/221223/6876</span> <span class="sd"> 1</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="k">if</span> <span class="n">a</span> <span class="o">&gt;=</span> <span class="n">p</span> <span class="ow">or</span> <span class="n">a</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="n">calculateLegendre</span><span class="p">(</span><span class="n">a</span> <span class="o">%</span> <span class="n">p</span><span class="p">,</span> <span class="n">p</span><span class="p">)</span> <span class="k">elif</span> <span class="n">a</span> <span class="o">==</span> <span class="mi">0</span> <span class="ow">or</span> <span class="n">a</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="n">a</span> <span class="k">elif</span> <span class="n">a</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span> <span class="k">if</span> <span class="n">p</span><span class="o">%</span><span class="mi">8</span> <span class="o">==</span> <span class="mi">1</span> <span class="ow">or</span> <span class="n">p</span><span class="o">%</span><span class="mi">8</span> <span class="o">==</span> <span class="mi">7</span><span class="p">:</span> <span class="k">return</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="o">-</span><span class="mi">1</span> <span class="k">elif</span> <span class="n">a</span> <span class="o">==</span> <span class="n">p</span><span class="o">-</span><span class="mi">1</span><span class="p">:</span> <span class="k">if</span> <span class="n">p</span><span class="o">%</span><span class="mi">4</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="o">-</span><span class="mi">1</span> <span class="k">elif</span> <span class="ow">not</span> <span class="n">isPrime</span><span class="p">(</span><span class="n">a</span><span class="p">):</span> <span class="n">factors</span> <span class="o">=</span> <span class="n">factorize</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="n">product</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">pi</span> <span class="ow">in</span> <span class="n">factors</span><span class="p">:</span> <span class="n">product</span> <span class="o">*=</span> <span class="n">calculateLegendre</span><span class="p">(</span><span class="n">pi</span><span class="p">,</span> <span class="n">p</span><span class="p">)</span> <span class="k">return</span> <span class="n">product</span> <span class="k">else</span><span class="p">:</span> <span class="k">if</span> <span class="p">((</span><span class="n">p</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="o">==</span><span class="mi">0</span> <span class="ow">or</span> <span class="p">((</span><span class="n">a</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="o">==</span><span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="n">calculateLegendre</span><span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="n">a</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">*</span><span class="n">calculateLegendre</span><span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="n">a</span><span class="p">)</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">doctest</span> <span class="n">doctest</span><span class="o">.</span><span class="n">testmod</span><span class="p">()</span></code></pre></div> <h2>More</h2> <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/eaz">Rules how to calculate with Legendre symbols</a></li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/Calculate-Legendre">Python and Pseudocode source files</a></li> </ul> How many Homomorphisms exist between Z/nZ and Z/mZ? //martin-thoma.com/how-many-homomorphisms-exist-between-znz-and-zmz/ Tue, 27 Aug 2013 15:26:38 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-many-homomorphisms-exist-between-znz-and-zmz <p>Today I’ve wondered how many homomorphisms are between the groups <code>$(\mathbb{Z}/n\mathbb{Z},+)$</code> and <code>$(\mathbb{Z}/m\mathbb{Z},+)$</code> with <code>$m, n \geq 2$</code>. Does it make a difference if I use + or <code>$\cdot$</code> as operators?</p> <p>Let <code>$M := (\mathbb{Z}/m\mathbb{Z},+)$</code> and <code>$N := (\mathbb{Z}/n\mathbb{Z},+)$</code> be groups and <code>$\varphi: M \rightarrow N$</code> be a group homomorphism. Let <code>$H := \{\varphi: M \rightarrow N\}$</code></p> <p>Some fundamental theorems (which I’m not going to prove) are:</p> <ol class="roman"> <li>`$\varphi(M)$` is a group.</li> <li>`$K_\varphi := \{m \in M | \varphi(m) = e_N\}$` is a group.</li> <li><a href="http://en.wikipedia.org/wiki/Lagrange%27s_theorem_(group_theory)">Lagrange's theorem</a>: `$H \leq G \Rightarrow \#H | \# G$`</li> <li>`$\varphi(1)$` defines the complete homomorphism as `$\varphi(n) = \varphi(1 + (n-1)) = \varphi(1) + \varphi(n-1)$`</li> <li>`$\varphi(1) = 0$` is always a homomorphism (that maps everything to 0).</li> </ol> <h2>`$m = n$`</h2> <p><strong>Theorem</strong>: <code>$n=m \Rightarrow |H|=n$</code> <strong>Proof</strong>: You can map <code>$1$</code> to <code>$n$</code> values <code>$\stackrel{(IV)}{\Rightarrow}$</code> there can’t be more than <code>$n$</code> homomorphisms.</p> <p>For every <code>$i \in \{0, \dots, n-1\}$</code> exists an homomorphism <code>$\varphi_i(1) = i$</code>: <code>$ \begin{align} \varphi(a) + \varphi(b) &amp;= (ai \mod n) + (bi \mod n)\\ &amp;= ai + bi \mod n\\ &amp;= (a+b)i \mod n\\ &amp;= \varphi(a+b) \end{align} $</code></p> <p>This means, that all of them are actually homomorphisms. For different <code>$i,j \in \{0, \dots, n-1\}$</code> the homomorphisms <code>$\varphi_i$</code> and <code>$\varphi_j$</code> are different. So we really have <code>$n$</code> homomorphisms <code>$\blacksquare$</code></p> <p>My first thought was that it’s only a permutation, but</p> <table> <tr><th>`$m \in M$`</th> <td>0</td><td>1</td><td>2</td><td>3</td><td>4</td><td>5</td></tr> <tr><th>`$\varphi(m) \in N$`</th><td>0</td><td>3</td><td>0</td><td>3</td><td>0</td><td>3</td></tr> </table> <p>is not a permutation, but a homomorphism.</p> <h2>Distinct primes</h2> <p><strong>Theorem</strong>: <code>$n, m \in \mathbb{P}, n \neq m \Rightarrow |H| = 1$</code> <strong>Proof</strong>:</p> <p>Let <code>$n, m \in \mathbb{P}, n \neq m$</code>.</p> <p><u>Part 1</u>: <code>$1 \leq |H|$</code></p> <p>This follows directly from (V).</p> <p><u>Part 2</u>: <code>$|H| \leq 1$</code></p> <p>We know that <code>$\begin{align} \stackrel{(I)+(III)}{\Rightarrow} &amp;\# \varphi(M) | \# N\\ \stackrel{n \in \mathbb{P}}{\Rightarrow} &amp;\# \varphi(M) \in \{1, n\} \end{align}$</code></p> <p>and</p> <p><code>$\begin{align} \stackrel{(II)+(III)}{\Rightarrow} &amp;\# K_\varphi | \# M\\ \stackrel{m \in \mathbb{P}}{\Rightarrow} &amp;\# K_\varphi \in \{1, m\} \end{align}$</code></p> <p>Case 1: <code>$m &gt; n$</code></p> <p>Now the kernel can’t be trivial anymore, so <code>$\# K_\varphi = m$</code>. This means that everything is mapped to 0. There is only one homomorphism that does so.</p> <p>Case 2: <code>$m &lt; n$</code></p> <p>Now the image <code>$\varphi(M)$</code> can’t be all of <code>$N$</code>. This means <code>$\varphi(M) = 1$</code> which is again the 0-mapping <code>$\blacksquare$</code></p> <h2>Any `$n$` and `$m$`</h2> <p><strong>Theorem</strong>: <code>$|H| = gcd(n, m)$</code> <strong>Proof</strong>:</p> <p>First a sanity check: The theorems above are special cases of this theorem. Let’s try to prove it.</p> <p>Let <code>$n$</code> be composed of primes <code>$p_1, \dots, p_x$</code> (where <code>$p_i = p_j$</code> is allowed). Then <code>$N = \mathbb{Z}/n\mathbb{Z} \cong \mathbb{Z}/p_1\mathbb{Z} \times \mathbb{Z}/p_2\mathbb{Z} \times \cdots \times \mathbb{Z}/p_x\mathbb{Z}$</code> according to the <a href="http://en.wikipedia.org/wiki/Chinese_remainder_theorem">Chinese remainder theorem</a>. The same is true for <code>$M$</code>. As there are <code>$p_i$</code> homomorphisms between <code>$\mathbb{Z}/p_i\mathbb{Z}$</code> and <code>$\mathbb{Z}/p_j\mathbb{Z}$</code> with <code>$p_i = p_j$</code> and as you can take a <code>$p_i$</code> from the left and a <code>$p_j$</code> from the right you can combine the different homomorphisms. So it is basically a combinatoric problem. As everything (except for same primes) will only have 1 homomorphism, you have to multiply the number of homomophisms for each pair <code>$(p_i, p_j)$</code>. But this is simply the gcd <code>$\blacksquare$</code></p> <h2>`$(\mathbb{Z}/n\mathbb{Z}, \cdot)$`</h2> <p>What changes when we use <code>$(\mathbb{Z}/n\mathbb{Z}, \cdot)$</code> and <code>$(\mathbb{Z}/m\mathbb{Z}, \cdot)$</code>?</p> <p>Well, first of all <code>$m$</code> and <code>$n$</code> have to be primes. Otherwise, not every element would have an inverse. Second, you have to exclude 0. Which means we only use units:</p> <p><code>$(\mathbb{Z}/n\mathbb{Z}, \cdot)^\times$</code> and <code>$(\mathbb{Z}/m\mathbb{Z}, \cdot)^\times$</code></p> <p>According to the German Wikipedia (<a href="http://de.wikipedia.org/wiki/Prime_Restklassengruppe">source</a>):</p> <blockquote>`$(\mathbb{Z}/n\mathbb{Z})^\times$` is cyclic `$:\Leftrightarrow n \in \{p^r, 2p^r | p \in \mathbb{P}, r \in \mathbb{N}_{\geq 1}\}$`</blockquote> <p>So there is no simple way to reduce it to the same proofs. But I’ve created a little <a href="https://gist.github.com/MartinThoma/6353473">script that automatically finds homomorphisms</a>.</p> <h2>Related</h2> <ul> <li><a href="http://math.stackexchange.com/q/45663/6876">Quick way to find the number of the group homomorphisms ϕ:Z3&rarr;Z6?</a></li> </ul> Why is the stabilizer subgroup a subgroup? //martin-thoma.com/stabilizer-subgroup-subgroup/ Mon, 26 Aug 2013 11:24:54 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/stabilizer-subgroup-subgroup <div class="definition">Let `$(G, \cdot)$` be a group and `$M$` a set. A <strong>group action</strong> is a function: `$G \circ M \rightarrow M$` that satisfies the following two conditions <ul> <li>Identity: `$\forall m \in M: e_G \circ m = m$`</li> <li>Associativity: `$\forall g, h \in G, m \in M: (g \cdot h) \circ m= g \circ (h \circ m)$`</li> </ul></div> <div class="definition">Let `$m \in M$`. Then `$G_m := \{g \in G | g \circ m = m\}$` is called the <strong>stabilizer</strong> of `$m$`.</div> <p><strong>Theorem</strong>: <code>$G_m$</code> is a group</p> <p><strong>Proof</strong>:</p> <p>Let <code>$m \in M$</code>.</p> <p><code>$\stackrel{identity}{\Rightarrow}e_G \in G_m$</code></p> <p>Let <code>$a \in G_m$</code>. This means, that <code>$a \circ m = m$</code>. And <code>$\exists a^{-1} \in G$</code>, as <code>$G$</code> is a group. <code>$a^{-1} \cdot a = e_G$</code>, this means <code>$(a^{-1} \cdot a) \circ m = m$</code>. <code>$\stackrel{associativity}{\Rightarrow}a^{-1} \circ (a \circ m) = m \Leftrightarrow a^{-1} \circ m = m \Leftrightarrow a^{-1} \in G_m$</code></p> <p>Let <code>$a, b \in G_m$</code>. Then: <code>$a \circ m = m$</code> and <code>$b \circ m = m$</code></p> <p><code>$\Rightarrow a \circ (b \circ m) = m$</code> <code>$\stackrel{associativity}{\Rightarrow} (a \cdot b) \circ m = m \Leftrightarrow (a \cdot b) \in G_m \blacksquare$</code></p> Why is the intersection of two normal subgroups a normal subgroup? //martin-thoma.com/intersection-two-normal-subgroups-normal-subgroup/ Sun, 25 Aug 2013 18:04:56 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/intersection-two-normal-subgroups-normal-subgroup <p>Let <code>$(G, \cdot)$</code> be a group and <code>$X \lhd G$</code> and <code>$Y \lhd G$</code> be two normal subgroups.</p> <p>I will show this in two steps:</p> <ol> <li>Show that `$X \cap Y$` is a group</li> <li>Show that `$X \cap Y$` is a normal group of `$(G, \cdot)$`</li> </ol> <h2>Intersection of two subgroups is a subgroup</h2> <p><strong>Theorem</strong>: <code>$(X \cap Y) \leq G$</code> <strong>Proof</strong>:</p> <p><code>$X \cap Y$</code> is not empty: <code>$e_G \in X \land e_G \in Y \Rightarrow e_G \in (X \cap Y)$</code></p> <p><code>$X \cap Y$</code> has inverse elements. Let <code>$a \in (X \cap Y)$</code>. As a is in <code>$X$</code> and <code>$X$</code> is a group, <code>$a^{-1} \in X$</code>. The same is true for <code>$Y$</code>. So: <code>$\forall a \in (X \cap Y) \exists a^{-1} \in (X \cap Y): a \cdot a^{-1} = a^{-1} \cdot a = e_G$</code></p> <p><code>$\forall a,b \in (X \cap Y): a \cdot b^{-1} \in (X \cap Y)$</code>, because both, <code>$a$</code> and <code>$b^{-1}$</code> are in <code>$X$</code>. As <code>$X$</code> is a group, the result has to be in <code>$X$</code>. Same argumentation for <code>$Y$</code>. Then the result is in <code>$X$</code> and <code>$Y \blacksquare$</code></p> <h2>Intersection of two normal subgroups is normal</h2> <p>First the definition of a normal subgroup:</p> <div class="definition">Let `$N \leq G$` be a subgroup of `$G$`. `$N \lhd G :\Leftrightarrow \forall n \in N \forall g \in G: g \cdot n \cdot g^{-1} \in N$`</div> <p><strong>Theorem</strong>: <code>$(X \cap Y) \lhd G$</code></p> <p><strong>Proof</strong>:</p> <p><code>$X \cap Y$</code> is a subgroup of <code>$G$</code> as I have proved above.</p> <p><code>$\forall n \in (X \cap Y) \forall g \in G: g \cdot n \cdot g^{-1} \in X$</code> and <code>$\forall n \in (X \cap Y) \forall g \in G: g \cdot n \cdot g^{-1} \in Y$</code></p> <p><code>$\Rightarrow \forall n \in (X \cap Y) \forall g \in G: g \cdot n \cdot g^{-1} \in (X \cap Y)$</code></p> <p><code>$\Rightarrow (X \cap Y) \lhd G \blacksquare$</code></p> How to analyze Mailman archives //martin-thoma.com/how-to-analyze-mailman-archives/ Sun, 18 Aug 2013 21:23:49 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-analyze-mailman-archives <p>All mailing lists I use are <a href="http://en.wikipedia.org/wiki/GNU_Mailman">GNU Mailman</a> lists. This software provides archives of all Emails that were send over the list.</p> <p>They look like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/08/mailman-list-archive-300x277.png"><img src="../images/2013/08/mailman-list-archive-300x277.png" alt="GNU Mailman list archive" width="" height="" class="size-medium wp-image-76298" /></a><p class="wp-caption-text">GNU Mailman list archive</p></div> <p>Once in a while, I would like to search if a topic was already discussed. Here is how you can do it:</p> <h2>Download archives</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">wget --save-cookies cookie.txt --post-data <span class="s1">&#39;username=user&amp;password=pass&#39;</span> -A gz -m -p -E -k -K -np https://lists.abc.org/mailman/blub/</code></pre></div> <h2>Rename archives</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="k">for</span> file in *.txt.gz<span class="p">;</span> <span class="k">do</span> mv <span class="s2">&quot;`$file&quot;</span> <span class="s2">&quot;$`{file%.txt.gz}.txt&quot;</span><span class="p">;</span> <span class="k">done</span></code></pre></div> <p>To make them sortable:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>for file in *January.txt; do mv &quot;$file&quot; &quot;${file%January.txt}01.txt&quot;; done for file in *February.txt; do mv &quot;$file&quot; &quot;${file%February.txt}02.txt&quot;; done for file in *March.txt; do mv &quot;$file&quot; &quot;${file%March.txt}03.txt&quot;; done for file in *April.txt; do mv &quot;$file&quot; &quot;${file%January.txt}04.txt&quot;; done for file in *May.txt; do mv &quot;$file&quot; &quot;${file%May.txt}05.txt&quot;; done for file in *June.txt; do mv &quot;$file&quot; &quot;${file%June.txt}06.txt&quot;; done for file in *July.txt; do mv &quot;$file&quot; &quot;${file%July.txt}07.txt&quot;; done for file in *August.txt; do mv &quot;$file&quot; &quot;${file%August.txt}08.txt&quot;; done for file in *September.txt; do mv &quot;$file&quot; &quot;${file%September.txt}09.txt&quot;; done for file in *October.txt; do mv &quot;$file&quot; &quot;${file%October.txt}10.txt&quot;; done for file in *November.txt; do mv &quot;$file&quot; &quot;${file%November.txt}11.txt&quot;; done for file in *December.txt; do mv &quot;$file&quot; &quot;${file%December.txt}12.txt&quot;; done </pre></div> </div> </div> <h2>Analyze them</h2> <p>To analyze the archives properly, you should perhaps first import all emails in a relational database. But with <code>grep</code> you could also do simple keyword searches.</p> Audible //martin-thoma.com/audible/ Tue, 13 Aug 2013 00:58:21 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/audible <p>I have just decided to try Audible.de, the German part of <a href="http://en.wikipedia.org/wiki/Audible.com">Audible.com</a> which is “An Amazon Company”. They offer audiobooks. You have to know that I really like to listen to audiobooks when I can’t read and need some distraction.</p> <p>Everybody who lives in Germany and buys something at Amazon knows the coupons that you get with a purchase:</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/amazon-audible-coupon-front.jpg" class="image"><img src="//martin-thoma.com/captions/amazon-audible-coupon-front.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Audible coupon - front</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/amazon-audible-coupon-back.jpg" class="image"><img src="//martin-thoma.com/captions/amazon-audible-coupon-back.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Audible coupon - back</div></div></li></ul> <h2>Buying audiobooks</h2> <p>Buying the audiobook I liked (“Darknet” from Daniel Suarez) was just as I knew it from Amazon. <span class="hint" text="Why the hell do they use another design?">Another design</span>, but even my bank account data is there. After purchasing it, I wanted to listen to it:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/08/bought-audio-book-300x166.png"><img src="../images/2013/08/bought-audio-book-300x166.png" alt="After having bought an audiobook" width="" height="" class="size-medium wp-image-76101" /></a><p class="wp-caption-text">After having bought an audiobook</p></div> <p>After clicking on “my library” I get to this page:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/08/audible-my-library-300x168.png"><img src="../images/2013/08/audible-my-library-300x168.png" alt="My library" width="" height="" class="size-medium wp-image-76121" /></a><p class="wp-caption-text">My library</p></div> <p>A click on “Start Audible-Assistant” redirects to:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/08/assistant-software-download-300x168.png"><img src="../images/2013/08/assistant-software-download-300x168.png" alt="Software download assistant" width="" height="" class="size-medium wp-image-76131" /></a><p class="wp-caption-text">Software download assistant</p></div> <p>So I thought I could download it to my smartphone.</p> <h2>Android App</h2> <p>If the <a href="https://play.google.com/store/apps/details?id=com.audible.application">Audible Android App</a> was software for your computer, you would call it spyware:</p> <ul> <li>It requires the permission to add or change calendar dates,</li> <li>send E-mails to "guests" (whatever this means),</li> <li>pairing with Bluetooth devices,</li> <li>and some other stuff (which seems to be okay)</li> </ul> <p>Why the hell do they want to change my calendar dates? I only want to listen to audiobooks I’ve bought…</p> <p>This is not okay for me, so lets see if I can listen to it on my computer.</p> <h2>Linux</h2> <p>As so often, there is no support for Linux. But <a href="http://appdb.winehq.org/objectManager.php?sClass=application&amp;iId=1612">Wine</a> does a great job in bringing Windows applications to Linux. So I’ve installed the software:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/08/audible-manager-300x168.png"><img src="../images/2013/08/audible-manager-300x168.png" alt="Audible Manager" width="" height="" class="size-medium wp-image-76171" /></a><p class="wp-caption-text">Audible Manager</p></div> <p>I thought, maybe I need to activate it via the web interface. Back to image “Software download assistant”, click on “Add device” (the big orange button):</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/08/audible-assistant-300x168.png"><img src="../images/2013/08/audible-assistant-300x168.png" alt="Audible Web assistant" width="" height="" class="size-medium wp-image-76191" /></a><p class="wp-caption-text">Audible Web assistant</p></div> <h2>My E-mail</h2> <p>There seems to be no way for me to download an audiobook with Audible. As it’s now very late, I’ve contacted customer service and described the issue (12.08.2013, 23:00):</p> <blockquote>Sehr geehrte Damen und Herren, wenn ich mein Hörbuch herunterladen will, werde ich darauf hingewiesen, dass ich noch kein Gerät hinzugefügt habe. Wenn ich dann über den Link (http://www.audible.de/assistant) ein Gerät (meinen Linux-Computer auf dem der AudibleManager mit wine läuft) hinzufügen will, bekomme ich einen Fehler 404 (Seite nicht gefunden). Mit freundlichen Grüßen, Martin Thoma</blockquote> <p>Answer:</p> <blockquote>Lieber Herr Thoma, vielen Dank für Ihr freundliches Schreiben. Es tut uns leid, tatsächlich können wir unseren Service derzeit nicht auf Linux-Systemen anbieten. Ob es in Zukunft eine Unterstützung für Linux geben wird, können wir gegenwärtig leider nicht versprechen. Wir bitten um Ihr Verständnis. Wenn Sie den Manager bereits installiert haben und als Browser Firefox benutzen, dann sollten Sie das admhelper.adh Script mit dem AudibleDownloadHelper via wine öffnen können. Wir hoffen, dass dies eine gute Alternative für Sie ist und stehen bei allen weiteren Fragen gerne zur Verfügung. Ich wünsche Ihnen einen wunderbaren Tag. Herzliche Grüße [A name which I don't want to show here.] Audible-Kundenservice</blockquote> <h2>Virtual Box</h2> <p>I’ve finally got it to work. I’ve installed XP with Virtual Box.</p> <h2>Cancellation</h2> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-0.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-0.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 0</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-1.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-1.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 1</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-2.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-2.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 2</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-3.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-3.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 3</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-4.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-4.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 4</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-5.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-5.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 5</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-6.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-6.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 6</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/08/audible-kuendigung-step-7.png" class="image"><img src="//martin-thoma.com/captions/audible-kuendigung-step-7.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Step 7</div></div></li></ul> <h2>Conclusion</h2> <p><abbr title="Digital Rights Management">DRM</abbr> seems to be necessary for such a service. Okay, I want to get my free audiobook, so I have to accept this. But this one reason why the service SUCKS. It would be much easier to let the user download the audiobook as a simple MP3 / WAV / OGG file. Everybody can play these files.</p> <p>Do you want to install software for every service you want to purchase audiobooks / songs from? Please also consider that Amazon might close your account (<a href="http://www.faz.net/aktuell/finanzen/meine-finanzen/geld-ausgeben/nachrichten/amazon-sperrt-kunden-konten-angst-um-die-retoure-12315430.html">source</a>), so you can not simply stick with one provider.</p> <p>Currently, I can only say: Don’t use audible. It’s a terrible service.</p> Improving lecture notes: Job (almost) done! //martin-thoma.com/improving-lecture-notes-job-almost-done/ Sat, 10 Aug 2013 15:50:09 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/improving-lecture-notes-job-almost-done <p>Some of you might know that I’ve bin improving the lecture notes for the computer engineering lecture (digital electronics) since April 2013.</p> <h2>How I've got the job</h2> <p>This was kind of funny. I send Prof. Dr. Asfour some notes of passages that could be improved (mainly typos). About two days later he proposed me to correct it by myself. Another day later I signed the contract. I’ve never signed a contract that fast.</p> <h2>What I did</h2> <p>My job was</p> <ul> <li>to correct errors (German language, statements about computer science and LaTeX),</li> <li>find parts that were outdated and update them,</li> <li>find sections that were difficult to understand and simplify them and</li> <li>to make it easier to make changes in the future (Well, I don't think Prof. Dr. Asfour thought this was my job ... but I think it's important.)</li> </ul> <p>So Prof. Dr. Asfour created a SVN repository with all LaTeX sources of the latest lecture notes (which were already great!). He also sent me Emails he received from students who mentioned errors just like I did and some notes from a tutor who tried to improve the script some time ago.</p> <h2>Revisions</h2> <p>With <code>svn checkout svn://somepath@1 working-directory</code> you can checkout the first revision of a SVN repository.</p> <p>Total number of files and folders: <code>find . | wc -l</code></p> <ul> <li>Revision 1: 1885</li> <li>Revision 30: 1488</li> </ul> <p>How often did I change files (<a href="http://wirespeed.wordpress.com/2011/06/08/subversion-how-many-times-has-a-file-been-modified/">source</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>svn log -qvr 1:HEAD|perl -nle 'print if /^Changed paths:/ ... /^-+$/ and /^\s/' \ | sort | uniq -c | sort -n </pre></div> </div> </div> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="m">1</span> M /ti1.bib <span class="m">2</span> M / <span class="m">2</span> M /anhang-1.tex <span class="m">2</span> M /anhang-3.tex <span class="m">2</span> M /anhang-5.tex <span class="m">2</span> M /diss-report.cls <span class="m">2</span> M /figures/Makefile <span class="m">2</span> M /titel.tex <span class="m">2</span> M /zahlen_codes <span class="m">3</span> M /vorwort.tex <span class="m">7</span> M /einleitung.tex <span class="m">8</span> M /Makefile <span class="m">10</span> M /my_def.tex <span class="m">11</span> M /sw.tex <span class="m">14</span> M /arith.tex <span class="m">14</span> M /skript.tex <span class="m">16</span> M /daten.tex <span class="m">19</span> M /sn.tex <span class="m">22</span> M /README.txt <span class="m">28</span> M /skript.pdf</code></pre></div> <p>With <a href="https://sourceforge.net/projects/codeanalyze-gpl/">CodeAnalyzer</a> over all .tex files:</p> <table> <tr> <th>&nbsp;</th> <th>Revision 1</th> <th>Revision 30</th> </tr> <tr> <th>Total files</th> <td>31</td> <td>14</td> </tr> <tr> <th>Total Lines</th> <td>24,679</td> <td>11,077</td> </tr> <tr> <th>Avg Line Length</th> <td>39</td> <td>45</td> </tr> <tr> <th>Code Lines</th> <td>18,500</td> <td>8,967</td> </tr> <tr> <th>Comment Lines</th> <td>1,124</td> <td>871</td> </tr> <tr> <th>Whitespace Lines</th> <td>5,177</td> <td>1,391</td> </tr> <tr> <th>Resulting PDF pages</th> <td>229</td> <td>233</td> </tr> <tr> <th>Examples</th> <td>93 &lt;</td> <td>93</td> </tr> <tr> <th>Images</th> <td>211</td> <td>211</td> </tr> </table> <h2>StackExchange</h2> <p>I’ve learned quite a lot about LaTeX while correcting the document. My questions on StackExchange might reflect that:</p> <ul> <li>xfig: <ul> <li><a href="http://tex.stackexchange.com/q/109388/5645">What are epic macro, eepic macro and eepicemu macro in xfig?</a></li> <li><a href="http://tex.stackexchange.com/questions/115773/setfigfontnfss-vs-setfigfont">SetFigFontNFSS vs. SetFigFont</a></li> </ul> </li> <li><a href="http://tex.stackexchange.com/q/117704/5645">Quotation marks: Is there any difference between \grqq/\glqq and &ldquo;` / &rdquo;'?</a></li> <li><a href="http://tex.stackexchange.com/q/117751/5645">How to use nag?</a> - This gave me a lot of input what I could improve</li> <li><a href="http://tex.stackexchange.com/q/121725/5645">How should I prevent images from floating between list and paragraph before</a></li> <li><a href="http://tex.stackexchange.com/q/125657/5645">Can I tell LaTeX to break a list?</a></li> <li><a href="http://tex.stackexchange.com/q/126790/5645">How can I prevent breaks in a custom environment?</a></li> <li><a href="http://tex.stackexchange.com/q/127561/5645">Is it possible to define an environment that might not be displayed?</a></li> <li><a href="http://stackoverflow.com/q/18158930/562769">Why doesn't grep give the matching line?</a></li> </ul> <p>And some language questions:</p> <ul> <li><a href="http://german.stackexchange.com/q/7027/655">Nummerierung im Text</a></li> <li><a href="http://german.stackexchange.com/q/6589/655">Gibt es ein Verb f&uuml;r &ldquo;Ein Zeichen wird durch seine Escape-Sequenz ersetzt&rdquo;?</a></li> <li><a href="http://german.stackexchange.com/q/6154/655">&ldquo;Theoretische Informatik&rdquo; oder &ldquo;theoretische Informatik&rdquo;</a></li> </ul> <h2>What I've learned</h2> <ul> <li>You can open file skript.tex on line 1234 with <code>vim +1234 skript.tex</code></li> <li><code>grep -rniI</code>, <code>find</code>, <code>xargs</code>, make and <a href="http://en.wikipedia.org/wiki/Meld_(software)">Meld</a> are VERY useful</li> <li>I like Git more than SVN (because I don't need internet to commit)</li> <li>nag package is interesting</li> <li>There seems to be no good way to create images for digital electronics which might contain LaTeX. xfig is the best I found, but it is very hard to use.</li> </ul> <h2>Conclusion</h2> <p>Working as a “Skript-HiWi” is easy work, but more time consuming than you might think. Even if you know how to work with LaTeX. Rebuilding a big document takes some time.</p> <p>I was astonished that there were some topics which I didn’t understand yet. After I’ve prepared for the exam, I thought I knew everything in the lecture notes. Obviously, this was not the case (or I forgot how to do division with twos complement meanwhile).</p> Why everybody should know about conditional probability //martin-thoma.com/why-everybody-should-know-about-conditional-probability/ Tue, 23 Jul 2013 15:37:39 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/why-everybody-should-know-about-conditional-probability <p>Probability theory is difficult, but I think everybody should be taught basics in this subject. Why? Because it is relevant for everybody.</p> <p>Suppose you go to the doctor to make a cancer test. The test is positive. That means you have cancer, right? Wrong!</p> <h2>Basics</h2> <p>A probability is a numerical value in [0, 1] that is assigned to events (or lets rather say outcomes of an experiment). A probability can never be less than zero and never be more than one.</p> <p>The sum of all probabilities of all outcomes of one experiment is always 1.</p> <p>Example: Your experiment <code>$x$</code> could be throwing a coin. The outcome of your experiment is either head or tails. So if <code>$Pr[x = \text{head}] = 0.6$</code>, then <code>$Pr[x = \text{tail}] = 0.4$</code>.</p> <p>Now you might argue that the coin can also stand on its border. This would result in a different model of the situation with different probabilities, e.g.:</p> <p><code>$Pr[x = \text{head}] = 0.559$</code>, <code>$Pr[x = \text{border}] = 0.001$</code> and <code>$Pr[x = \text{tail}] = 0.4$</code>.</p> <p>Another very important rule is Bayes rule:</p> <p><code>$Pr[A|B] = \frac{Pr[B|A] \cdot Pr[A]}{Pr[B]}$</code></p> <p>This works also with more variables:</p> <p><code>$Pr[A|BC] = \frac{Pr[B|AC] \cdot Pr[A|C]}{Pr[B|C]}$</code></p> <h2>Cancer</h2> <p>Lets say the probability of having cancer is <code>$Pr[C] = 0.01$</code>. This means the probability of not having cancer is <code>$Pr[\neg C] = 0.99$</code>.</p> <p>Now you have cancer tests. They can either be positive (+) which means they say you have cancer. Or they are negative (-), which means according to the test, you don’t have cancer.</p> <p>They are not always working as expected. So you get so called “false positives” and “false negatives”.</p> <p>A false positive is a positive result, while it should be negative. So the test says you have cancer, while you don’t have cancer. It is denoted by <code>$Pr[+ | \neg C] = 0.2$</code>.</p> <p>A false negative is a negative result, while it should be positive. So the test says you don’t have cancer, but you actually have cancer. It is denoted by <code>$Pr[- | C] = 0.1$</code>.</p> <p>You should note that <code>$Pr[+ | \neg C] + Pr[- | C] = 0.2 + 0.1 = 0.3 \neq 1$</code>. Why is this the case? Because the test might also not be related at all to you having cancer.</p> <p>But <code>$Pr[+ | \neg C] + Pr[- | \neg C]$</code> has to be 1 and <code>$Pr[+ | C] + Pr[- | C]$</code> also has to be one.</p> <p>So you can draw this table:</p> <table class="wikitable" style="width:auto;"> <tr> <th>`$Pr[\text{Testresult}|\text{Cancer}]$`</th> <th>`$C$`</th> <th>`$\neg C$`</th> </tr> <tr> <th>`$+$`</th> <td style="background-color:lime;">`$0.9$`</td> <td style="background-color:red;">`$0.2$`</td> </tr> <tr> <th>`$-$`</th> <td style="background-color:red;">`$0.1$`</td> <td style="background-color:lime;">`$0.8$`</td> </tr> </table> <p>You can see that the correct results are much more likely than the wrong ones.</p> <h2>Some intermediate results</h2> <p>How likely is a positive / negative test result? <code>$\begin{align} Pr[+] &amp;= Pr[+|C] \cdot Pr[C] + Pr[+| \neg C] \cdot Pr[\neg C] = 0.207\\ Pr[-] &amp;= Pr[-|C] \cdot Pr[C] + Pr[-| \neg C] \cdot Pr[\neg C] = 0.793 \end{align}$</code></p> <p>How likely are the combinations? (This time you don’t know if you have cancer):</p> <table class="wikitable" style="width:auto;"> <tr> <th>`$Pr[\text{Testresult}, \text{Cancer}]$`</th> <th>`$C$`</th> <th>`$\neg C$`</th> </tr> <tr> <th>`$+$`</th> <td>`$0.009$`</td> <td>`$0.198$`</td> </tr> <tr> <th>`$-$`</th> <td>`$0.001$`</td> <td>`$0.792$`</td> </tr> </table> <h2>Reversing it</h2> <p>It is quite likely that you would like to know how likely it is that you have cancer. Without a test, you know:</p> <p><code>$\begin{align} Pr[C] &amp;= 0.01\\ Pr[\neg C] &amp;= 0.99 \end{align}$</code></p> <p>Now you get a positive test result. How likely is it that you have cancer? In other words: Calculate <code>$Pr[C|+]$</code></p> <p><code>$\begin{align} Pr[C|+] &amp;= \frac{Pr[C, +]}{Pr[+]} = \frac{0.009}{0.207} = \frac{1}{23} \approx 0.043\\ Pr[\neg C|+] &amp;= 1 - \frac{1}{23} = \frac{22}{23} \approx 0.957\\ Pr[C|-] &amp;= \frac{0.001}{0.793} = \frac{1}{793} \approx 0.001\\ Pr[\neg C|-] &amp;= 1 - \frac{1}{793} = \frac{792}{793} \approx 0.999 \end{align}$</code></p> <p>How would you interpret these results? I’d say: When you get a positive result you shouldn’t really worry. But perhaps you should make other tests. When you get a negative results you can be very sure that you don’t have cancer.</p> <h2>Testing again</h2> <p>A very natural approach to a positive test result might be taking the same test again. How does this influence the probability?</p> <p>There are four possibilities what could have happened:</p> <ul> <li>You have cancer: <ul> <li>Second test was negative</li> <li>Second test was positive</li> </ul> </li> <li>You don't have cancer: <ul> <li>Second test was negative</li> <li>Second test was positive</li> </ul> </li> </ul> <p>First of all, I compare some intermediate results <code>$ \begin{align} Pr[++] &amp;= Pr[C] \cdot Pr[+|C] \cdot Pr[+|C] + Pr[\neg C] \cdot Pr[+|\neg C] \cdot Pr[+|\neg C]\\ &amp;= 0.477 \neq 0.042849 = 0.207^2 = (Pr[+])^2\\ Pr[+-] &amp;= Pr[C] \cdot Pr[+|C] \cdot Pr[-|C] + Pr[\neg C] \cdot Pr[+|\neg C] \cdot Pr[-|\neg C] \\ &amp;= 0.01 \cdot 0.9 \cdot 0.1 + 0.99 \cdot 0.2 \cdot 0.8\\ &amp;= 0.1593\\ Pr[C,+,+] &amp;= Pr[C] \cdot Pr[+ | C]^2 = 0.01 \cdot 0.9^2 = 0.0081\\ Pr[C,+,-] &amp;= Pr[C] \cdot Pr[+ | C] \cdot Pr[-|C] = 0.01 \cdot 0.9 \cdot 0.1 = 0.0009\\ Pr[C|++] &amp;= \frac{Pr[C,+,+]}{Pr[++]} = \frac{0.0081}{0.207^2} = \frac{9}{530} \approx 0.170\\ Pr[C|+-] &amp;= \frac{Pr[C,+,-]}{Pr[+-]} = \frac{0.0009}{0.1593} = \frac{1}{177} \approx 0.006 \end{align} $</code></p> <p>Woooha! So if one test says you have cancer, don’t worry. When two tests say you have cancer, you have a 17% chance of having cancer.</p> <p>On the other hand: One negative and one positive test is better than no test at all, because without a test you have a probability of 0.01 to have cancer. With both tests, you only have a probability of 0.006.</p> <h2>Why probability is important for you</h2> <p>As you might have seen, your intuition about probability is wrong. But we hear numbers all the time. It is important for us to understand them, so we should drop our intuition and learn how to use those numbers.</p> Kollisionsresistente Hashfunktionen und Einwegfunktionen //martin-thoma.com/kollisionsresistente-hashfunktionen-und-einwegfunktionen/ Tue, 23 Jul 2013 10:05:24 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/kollisionsresistente-hashfunktionen-und-einwegfunktionen <h2>Definitionen</h2> <div class="definition"> Sei `$f:X \rightarrow Y$` eine Funktion. `$f$` heißt eine Einwegfunktion, genau dann wenn für alle `$x \in X$` gilt: <ul> <li>`$y := f(x)$` kann in Polynomialzeit berechnet werden</li> <li>Für die Berechnung eines Urbildes `$x$` aus `$y$` existiert kein randomisierter Algorithmus, der in Polynomialzeit läuft.</li> </ul> </div> <div class="definition"> Eine Funktion `$H:\{0,1\}^* \rightarrow \{0,1\}^k$` heißt <strong>kollisionsresistente Hashfunktion</strong>, wenn gilt: Jeder effiziente Algorithmus findet nur mit kleiner Wahrscheinlichkeit eine Kollision. </div> <p>Was heißt „kleine Wahrscheinlichkeit“? Nach dem Auswerten der Funktion <code>$H$</code> für <code>$x_1, x_2, \dots x_n$</code> sollte die Wahrscheinlichkeit nicht signifikant höher sein als <code>$\displaystyle 1-\frac{n!\cdot{{2^k} \choose n}}{{2^k}^n}$</code> Diese Wahrscheinlichkeit kommt von dem <a href="http://de.wikipedia.org/wiki/Geburtstagsparadoxon">Geburtstagsparadoxon</a> bzw. dem <a href="http://de.wikipedia.org/wiki/Schubfachprinzip">Schubfachprinzip</a>. Wir haben <code>$2^k$</code> Schubfächer (Funktionswerte) in die wir die <code>$x_i$</code> (Urbilder) einordnen können.</p> <h2>Satz</h2> <p><strong>Behauptung</strong>: Jede kollisionsresistente Hashfunktion ist eine Einwegfunktion. <strong>Beweis</strong>: durch Widerspruch Sei <code>$f$</code> eine kollisionsresistente Hashfunktion <u>Annahme</u>: <code>$f$</code> ist keine Einwegfunktion</p> <p>Dann existiert ein Angreifer <code>$\mathcal{A}$</code>, der für eine Bild <code>$f(x)$</code> ein <code>$x'$</code> findet, sodass <code>$f(x) = f(x')$</code> gilt.</p> <p>Der Angreifer <code>$\mathcal{B}$</code> macht nichts anderes, als zufällig Werte <code>$x \in \{0,1\}^{2k}$</code> zu wählen, <code>$f(x)$</code> zu berechnen, den Angreifer <code>$\mathcal{A}$</code> auf <code>$f(x)$</code> anzuwenden und zu überprüfen, ob das von <code>$\mathcal{A}$</code> gelieferte <code>$x' \neq x$</code> ist. Sobald das ein mal der Fall ist, hat der Angreifer gewonnen.</p> <p>Nun wenden wir <code>$f$</code> auf <code>$x \in \{0,1\}^{2k}$</code> an. Es gilt:</p> <p><code>$Pr_x[\underbrace{|f^{-1}(f(x))|}_{\substack{\text{Anzahl der Urbilder}\\\text{zum Hashwert} f(x)} } = 1] \leq \frac{2^k}{2^{2k}} = \frac{1}{2^k}$</code>.</p> <p>Die <code>$2^k$</code> im Zähler stehen für die Funktionswerte und die <code>$2^{2k}$</code> für die Urbilder.</p> <p>Nun ist <code>$\frac{1}{2^k}$</code> eine vernachlässigbare Funktion.</p> <p><code>$\Rightarrow$</code> Die Wahrscheinlichkeit, dass wir keine Kollsion finden ist vernachlässigbar.</p> <p><code>$\Rightarrow$</code> Mit signifikanter Wahrscheinlichkeit hat <code>$f(x)$</code> <code>$k \geq 2$</code> Urbilder.</p> <p><code>$\Rightarrow$</code> Die Wahrscheinlichkeit, dass <code>$\mathcal{B}$</code> Kollisionen findet ist etwa <code>$(1-\frac{1}{k}) \cdot m$</code>, wobei <code>$m$</code> die Anzahl der Widerholungen ist.</p> Signs that it is too hot outside //martin-thoma.com/signs-that-it-is-too-hot-outside/ Mon, 22 Jul 2013 22:59:13 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/signs-that-it-is-too-hot-outside <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/wetter.png" class="image"><img src="//martin-thoma.com/captions/wetter-2.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Weather map</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/wetterkarte-2013-07-26.png" class="image"><img src="//martin-thoma.com/captions/wetterkarte-2013-07-26-2.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Wetterkarte vom 26.07.2013</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/wetterkarte-2015-07-04.png" class="image"><img src="//martin-thoma.com/captions/wetterkarte-2015-07-04-2.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Wetterkarte vom 04.07.2015</div></div></li></ul> <h2>See also</h2> <ul> <li><a href="http://www.pleated-jeans.com/2013/07/02/20-signs-its-too-freaking-hot-outside/">20 Signs It&rsquo;s Too Freaking Hot Outside</a> - As a <a href="http://imgur.com/2XQla6k">single image on imgur.com</a></li> <li><a href="http://imgur.com/gallery/bOIHj">Another image</a></li> </ul> Simquadrat //martin-thoma.com/simquadrat/ Sun, 21 Jul 2013 18:18:12 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/simquadrat <p>Simquadrat ist ein Dienst von <a href="http://en.wikipedia.org/wiki/Sipgate">sipgate</a>. Das besondere daran ist, dass Simkarten verkauft werden, die eine Festnetznummer haben. Ich habe das ganze ausprobiert und will meine Erfahrungen nun teilen.</p> <h2>Das Angebot</h2> <p>Man geht auf <a href="https://www.simquadrat.de/">simquadrat.de</a>, bezahlt 4,95 Euro und bekommt eine <strong>Festnetznummer</strong> des Ortes, für den man die Postadresse angibt. Die meisten Leute, die ich kennen haben eine Festnetz-Flat. Das bedeutet, sie können mich kostenlos auf dem Handy anrufen. Toll, oder?</p> <p>Es ist ein <strong>Prepaid</strong>-Service. Das heißt, ich habe ein Guthaben, das ich vertelefonieren kann. Wenn das Guthaben weg ist, kann ich nicht mehr telefonieren. Das hat für mich vor allem den Vorteil, dass es keine versteckten Kosten gibt (bzw. diese micht nicht so hart treffen).</p> <p>Für <strong>10 Euro</strong> bekommt man eine <strong>1-Monat-Festnetzflat</strong>.</p> <h2>Die Bestellung</h2> <p>Die Bestellung auf <a href="https://www.simquadrat.de/signup">simquadrat.de</a> ist extrem einfach.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/simquadrat-bestellung-300x168.png"><img src="../images/2013/07/simquadrat-bestellung-300x168.png" alt="Bestellung bei Simquadrat" width="" height="" class="size-medium wp-image-74541" /></a><p class="wp-caption-text">Bestellung bei Simquadrat</p></div> <p>Nach drei Schritten ist man wirklich fertig. Die beiden E-Mails, die man dann bekommt, sind auch schön kurz:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/simquadrat-bestaetigung.png" class="image"><img src="//martin-thoma.com/captions/simquadrat-bestaetigung.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Simquadrat: Bestätigung</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/simquadrat-rechnung.png" class="image"><img src="//martin-thoma.com/captions/simquadrat-rechnung.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Simquadrat: Rechnung</div></div></li></ul> <p>Nach wenigen Tagen ist dann die Simkarte angekommen:</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/simquadrat-brief-1.jpg" class="image"><img src="//martin-thoma.com/captions/simquadrat-brief-1.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Brief, Seite 1</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/simquadrat-brief-2.jpg" class="image"><img src="//martin-thoma.com/captions/simquadrat-brief-2.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Brief, Seite 2</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/sipgate-simkarte.jpg" class="image"><img src="//martin-thoma.com/captions/sipgate-simkarte.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Simkarte von Sipgate</div></div></li></ul> <p>Wie man sieht, bekommt man eine Simkarte, wo man sich die richtige Größe herausbrechen kann. Micro- und Mini-Simkarten gehen also (bei Nano-Sim fürs iPhone bin ich mir nicht sicher, aber ich glaube auch das konnte man angeben).</p> <h2>Der Dienst</h2> <p>Simquadrat hat sofort funktioniert. Ich konnte telefonieren und SMS schreiben (die aber nicht bei meiner Freundin angekommen sind … aber das könnte auch gut an ihrem Handy/Anbieter liegen). Auch die Online-Benutzeroberfläche ist gut:</p> <div style="width: 271px" class="wp-caption aligncenter"><a href="../images/2013/07/simquadrat-eingeloggt-261x300.png"><img src="../images/2013/07/simquadrat-eingeloggt-261x300.png" alt="Simquadrat - So siehts aus, wenn man eingeloggt ist" width="" height="" class="size-medium wp-image-74601" /></a><p class="wp-caption-text">Simquadrat - So siehts aus, wenn man eingeloggt ist</p></div> <p>ABER: Die <strong>Telefonqualität ist unterirdisch</strong>. Ich erwarte, dass der Zugangsanbieter mein Gespräch in so guter Qualität überträgt, wie es mein Handy unterstützt. Mit Simyo ist die Qualität genauso gut wie über das Festnetz-Telefon. Laut prepaid-wiki nutzt Simquadrat wie Simyo das E-Plus-Netz. Ich habe mit meiner Freundin mit meinem Nexus 4 am selben Tag (mit einem Abstand von 10 Minuten für dem Simkartenwechsel) einmal mit Simyo und einmal mit Simquadrat telefoniert. Das ist, im Bezug auf die Qualität der Sprachübertragung, ein himmelweiter Unterschied.</p> <h2>Fazit</h2> <p>Wenn man sehr günstig in Deutschland erreichbar sein will, ist Simquadrat super. Sonst ist Simyo besser.</p> DNS-Services //martin-thoma.com/dns-services/ Sat, 20 Jul 2013 14:46:34 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/dns-services <p>I’ve just read (ok, now it’s over 3 months ago) that <a href="http://en.wikipedia.org/wiki/Google_Public_DNS">Google Public DNS</a> now supports DNSSEC (<a href="http://googleonlinesecurity.blogspot.de/2013/03/google-public-dns-now-supports-dnssec.html">source</a>).</p> <p>I was curious what I currently use on my Linux Mint 14 machine. The relevant file is <strong>/etc/resolv.conf</strong>:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">nameserver 127.0.1.1 # OpenDNS Fallback (configured by Linux Mint in /etc/resolvconf/resolv.conf.d/tail). nameserver 208.67.222.222 nameserver 208.67.220.220</code></pre></div> <h2>namebench</h2> <p>A programm called <a href="https://code.google.com/p/namebench">namebench</a> checks how fast several DNS configurations would be for you.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/namebench-300x222.png"><img src="../images/2013/03/namebench-300x222.png" alt="namebench" width="" height="" class="size-medium wp-image-62241" /></a><p class="wp-caption-text">namebench</p></div> <h2>Further reading</h2> <ul> <li><a href="http://wiki.ubuntuusers.de/Dnsmasq">Dnsmasq</a> (German)</li> <li><a href="http://www.debian.org/doc/manuals/debian-reference/ch05.en.html#_the_hostname_resolution">Debian manual - The hostname resolution</a>: explains where 127.0.1.1 comes from</li> </ul> SQL Injections //martin-thoma.com/sql-injections/ Thu, 11 Jul 2013 19:25:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sql-injections <p><abbr title="Structured Query Language">SQL</abbr> is a language that allows prorammers to access data in databases. Most of the time (always?) you pass your queries in form of strings to the database. In online services it is quite common that the programmer formulates a template and the user fills in variables.</p> <h2>Example: IMDb</h2> <p>Take a look at <a href="http://www.imdb.com/">IMDb</a>. Users can search for movies by title:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/imdb-harry-potter-query.png"><img src="//martin-thoma.com/captions/imdb-harry-potter-query.png" alt="IMDb: User Interface to search for a movie by title" width="299" height="194" class="size-medium" /></a><p class="wp-caption-text">IMDb: User Interface to search for a movie by title</p></div> <p>When you search for “Harry Potter” for example, the following happens:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/imdb-search-query-300x156.png"><img src="../images/2013/07/imdb-search-query-300x156.png" alt="Search query within URL and results" width="" height="" class="size-medium wp-image-73921" /></a><p class="wp-caption-text">Search query within URL and results</p></div> <p>You obviously interacted with imdb.com in a very dynamic way. The output of the website depends on what you typed in and IMDb has to search in its database for your search terms.</p> <p>The programmers might have created a query that looks like this</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> * <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">movie</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> title=<span style="color:#F00;background-color:#FAA">$</span>_GET[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">q</span><span style="color:#710">'</span></span>] </pre></div> </div> </div> <p>Where <code>$`_GET['q']</code> is your query.</p> <h2>Proof of concept</h2> <p>You need:</p> <ul> <li>Apache Web Server</li> <li>PHP</li> <li>MySQL</li> <li>PhpMyAdmin (for convenience)</li> </ul> <p>When you search for “LAMP” (for Linux users) or for “WAMP” (for Windows users) you find a lot of information how to install this.</p> <p>Place the following as <code>hack.php</code> in your web servers directory (might be <code>/var/www</code>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?</span> <span style="color:#950">$mysqlhost</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">localhost</span><span style="color:#710">&quot;</span></span>; <span style="color:#950">$mysqluser</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">root</span><span style="color:#710">&quot;</span></span>; <span style="color:#950">$mysqlpwd</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">asdfasdf</span><span style="color:#710">&quot;</span></span>; <span style="color:#950">$connection</span> = mysql_connect(<span style="color:#950">$mysqlhost</span>, <span style="color:#950">$mysqluser</span>, <span style="color:#950">$mysqlpwd</span>) <span style="color:#080;font-weight:bold">or</span> <span style="color:#369;font-weight:bold">die</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Your connection string was wrong</span><span style="color:#710">&quot;</span></span>); <span style="color:#950">$db_selected</span> = mysql_select_db(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">imdb</span><span style="color:#710">'</span></span>, <span style="color:#950">$connection</span>); <span style="color:#950">$q</span> = <span style="color:#369;font-weight:bold">$_GET</span>[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">q</span><span style="color:#710">'</span></span>]; <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$q</span> != <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span>) { <span style="color:#950">$result</span> = mysql_query(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">SELECT * FROM `movies` WHERE title='</span><span style="color:#950">$q</span><span style="color:#D20">'</span><span style="color:#710">&quot;</span></span>); <span style="color:#080;font-weight:bold">if</span> (!<span style="color:#950">$result</span>) { <span style="color:#369;font-weight:bold">die</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">MySQL query error: </span><span style="color:#710">'</span></span> . mysql_error()); } <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Found </span><span style="color:#710">&quot;</span></span>.mysql_num_rows(<span style="color:#950">$result</span>).<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> movies:&lt;br/&gt;</span><span style="color:#710">&quot;</span></span>; <span style="color:#080;font-weight:bold">while</span> (<span style="color:#950">$row</span> = mysql_fetch_assoc(<span style="color:#950">$result</span>)) { <span style="color:#369;font-weight:bold">echo</span> <span style="color:#950">$row</span>[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">id</span><span style="color:#710">&quot;</span></span>].<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">: </span><span style="color:#710">&quot;</span></span>.<span style="color:#950">$row</span>[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">title</span><span style="color:#710">&quot;</span></span>].<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">&lt;br/&gt;</span><span style="color:#710">&quot;</span></span>; } } <span style="font-weight:bold;color:#666">?&gt;</span> <span style="color:#070;font-weight:bold">&lt;form</span> <span style="color:#b48">method</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">get</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">action</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hack.php</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">text</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">q</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">submit</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;/form&gt;</span> </pre></div> </div> </div> <p>Now create a database called <code>imdb</code> with PHPMyAdmin and execute the following SQL:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">CREATE</span> <span style="color:#339;font-weight:bold">TABLE</span> <span style="color:#080;font-weight:bold">IF</span> <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#080;font-weight:bold">EXISTS</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">movies</span><span style="color:#710">`</span></span> ( <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#0a8;font-weight:bold">int</span>(<span style="color:#00D">11</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span> <span style="color:#088;font-weight:bold">AUTO_INCREMENT</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">title</span><span style="color:#710">`</span></span> <span style="color:#0a8;font-weight:bold">varchar</span>(<span style="color:#00D">255</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="color:#088;font-weight:bold">PRIMARY</span> <span style="color:#339;font-weight:bold">KEY</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) ) <span style="color:#088;font-weight:bold">AUTO_INCREMENT</span>=<span style="color:#00D">4</span>; <span style="color:#B06;font-weight:bold">INSERT</span> <span style="color:#B06;font-weight:bold">INTO</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">movies</span><span style="color:#710">`</span></span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">title</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">VALUES</span> (<span style="color:#00D">1</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Harry Potter</span><span style="color:#710">'</span></span>), (<span style="color:#00D">2</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Lord of the Rings</span><span style="color:#710">'</span></span>), (<span style="color:#00D">3</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Rise of the Silver Surfer</span><span style="color:#710">'</span></span>); <span style="color:#B06;font-weight:bold">CREATE</span> <span style="color:#339;font-weight:bold">TABLE</span> <span style="color:#080;font-weight:bold">IF</span> <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#080;font-weight:bold">EXISTS</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">users</span><span style="color:#710">`</span></span> ( <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span> <span style="color:#0a8;font-weight:bold">int</span>(<span style="color:#00D">11</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span> <span style="color:#088;font-weight:bold">AUTO_INCREMENT</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">username</span><span style="color:#710">`</span></span> <span style="color:#0a8;font-weight:bold">varchar</span>(<span style="color:#00D">255</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">password</span><span style="color:#710">`</span></span> <span style="color:#0a8;font-weight:bold">varchar</span>(<span style="color:#00D">32</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">email</span><span style="color:#710">`</span></span> <span style="color:#0a8;font-weight:bold">varchar</span>(<span style="color:#00D">255</span>) <span style="color:#080;font-weight:bold">NOT</span> <span style="color:#069">NULL</span>, <span style="color:#088;font-weight:bold">PRIMARY</span> <span style="color:#339;font-weight:bold">KEY</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>) ) <span style="color:#088;font-weight:bold">AUTO_INCREMENT</span>=<span style="color:#00D">3</span> ; <span style="color:#B06;font-weight:bold">INSERT</span> <span style="color:#B06;font-weight:bold">INTO</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">users</span><span style="color:#710">`</span></span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">id</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">username</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">password</span><span style="color:#710">`</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">email</span><span style="color:#710">`</span></span>) <span style="color:#080;font-weight:bold">VALUES</span> (<span style="color:#00D">1</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">admin</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">qewrtqwert</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">admin@imdb.com</span><span style="color:#710">'</span></span>), (<span style="color:#00D">2</span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">user</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">secret</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">mylittlepony@stupid.com</span><span style="color:#710">'</span></span>); </pre></div> </div> </div> <p>Now go to <a href="http://localhost/hack.php">http://localhost/hack.php</a>. It should look like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/hack-screenshot.png"><img src="//martin-thoma.com/captions/hack-screenshot.png" alt="Screenshot of my minimal example" width="298" height="85" class="size-medium wp-image-73971" /></a><p class="wp-caption-text">Screenshot of my minimal example</p></div> <p>When you search for “Harry Potter” it should show you “1: Harry Potter”. Note that there could be a lot of information, but I wanted to keep this example as small as possible.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/hack-normal-use.png"><img src="//martin-thoma.com/captions/hack-normal-use.png" alt="Normal use of the web service" width="297" height="77" class="size-medium" /></a><p class="wp-caption-text">Normal use of the web service</p></div> <p>This resulted in the following query:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> * <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">movies</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> title=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Harry Potter</span><span style="color:#710">'</span></span> </pre></div> </div> </div> <p>But a Hacker could also enter a string like this: <code>' OR '1'='1</code>:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/hack-hacky-use.png"><img src="//martin-thoma.com/captions/hack-hacky-use.png" alt="What a hacker could do" width="298" height="94" class="size-medium" /></a><p class="wp-caption-text">What a hacker could do</p></div> <p>Even worse, the attacker could know that you use MySQL. Then he might know that MySQL uses <a href="http://dev.mysql.com/doc/refman/5.1/en/information-schema.html">INFORMATION_SCHEMA tables</a>. He might enter this into the title input element:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20"> UNION SELECT table_name, table_type FROM information_schema.tables WHERE </span><span style="color:#710">'</span></span><span style="color:#00D">1</span><span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">=</span><span style="color:#710">'</span></span><span style="color:#00D">1</span> </pre></div> </div> </div> <p>which results in this query:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> * <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">movies</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHERE</span> title=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#710">'</span></span> <span style="color:#080;font-weight:bold">UNION</span> <span style="color:#B06;font-weight:bold">SELECT</span> table_name, table_type <span style="color:#080;font-weight:bold">FROM</span> information_schema.tables <span style="color:#080;font-weight:bold">WHERE</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">1</span><span style="color:#710">'</span></span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">1</span><span style="color:#710">'</span></span> </pre></div> </div> </div> <p>which gives:</p> <div style="width: 278px" class="wp-caption aligncenter"><a href="../images/2013/07/sql-injection-example.png"><img src="//martin-thoma.com/captions/sql-injection-example.png" alt="Attacker got all table names" width="268" height="300" class="size-medium" /></a><p class="wp-caption-text">Attacker got all table names</p></div> <p>This way, the attacker gets all table names from all databases on this machine. So he essentially can get everything stored in your database. And, of course, after getting everything he could drop it:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/07/exploits_of_a_mom.png"><img src="//martin-thoma.com/captions/exploits_of_a_mom.png" alt="xkcd 327: Exploits of a mom" width="299" height="92" class="size-medium" /></a><p class="wp-caption-text">xkcd 327: Exploits of a mom</p></div> <h2>History</h2> <p>Just a few famous examples to show you that this happens all the time:</p> <ul> <li>2005: USC admissions page (<a href="http://www.theregister.co.uk/2005/07/06/usc_site_cracked/">source</a>)</li> <li>2006: 800,000 datasets of personal information of students of UCLA (<a href="http://www.schneier.com/blog/archives/2006/12/major_privacy_b_1.html">source</a>)</li> <li>2008, 2009: Heartland Payment Systems; 130 million credit and debit cards (<a href="http://www.zdnet.com/blog/government/gonzales-just-tip-of-iceberg-in-heartland-attack/5252">source 1</a>, <a href="http://www.computerworld.com.au/article/315418/sql_injection_attacks_led_massive_data_breaches/">source 2</a>, see <a href="http://en.wikipedia.org/wiki/Albert_Gonzalez">Albert Gonzalez</a>)</li> <li>2010: Royal Navy Website; Passwords and Usernames stolen (<a href="http://www.eweek.com/c/a/Security/Hacker-Hits-British-Navy-Website-With-SQL-Injection-Attack-108377/">source</a>)</li> <li>2011: Sony: <blockquote>LulzSec says it accessed the passwords, email addresses, home addresses and dates of birth of one million users. The group says it also stole all admin details of Sony Pictures, including passwords. 75,000 music codes and 3.5 million music coupons were also accessed, according to the press release.</blockquote> (<a href="http://www.thewhir.com/web-hosting-news/hackers-attack-sony-pictures-with-single-sql-injection">source</a>)</li> <li>2011: Expedia (<a href="http://www.eweek.com/c/a/Security/Expedias-TripAdvisor-Member-Data-Stolen-in-Possible-SQL-Injection-Attack-522785/">source</a>)</li> <li>2011: MySql - Usernames and passwords stolen (<a href="http://www.infoworld.com/d/security/mysql-website-falls-victim-sql-injection-attack-155886">source 1</a>, <a href="http://seclists.org/fulldisclosure/2011/Mar/309">source 2</a>)</li> <li>2011: Comodo (<a href="http://www.infosecurity-magazine.com/view/18265/another-comodo-partner-attacked-using-sql-injection/">source 1</a>, <a href="http://www.heise.de/security/meldung/Erneut-Comodo-SSL-Registrar-gehackt-1250208.html">source 2</a>)</li> </ul> <h2>Solutions</h2> <ul> <li>Sanitize user input, e.g. with <a href="http://de2.php.net/mysql_real_escape_string">mysql_real_escape_string</a></li> <li>Use <a href="http://php.net/manual/en/pdo.prepared-statements.php">prepared statements</a></li> <li>Switch of <a href="http://php.net/manual/en/function.error-reporting.php">error reporting</a> (this makes attacks more difficult, but doesn't prevent them)</li> </ul> <h2>See also</h2> <ul> <li><a href="../challenge-websites/">Challenge Websites</a>: Try if you can write SQL injections yourself ☺</li> </ul> Medion Life MD 83962 E69229 //martin-thoma.com/medion-life-md-83962-e69229/ Tue, 09 Jul 2013 23:34:51 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/medion-life-md-83962-e69229 <p>Momentan kann man <a href="http://www.medion.com/de/prod/Lautsprecher+mit+Bluetooth+Funktion+MEDION%C2%AE+LIFE%C2%AE+E69229+(MD+83962)/50043426A1">diese Blootooth</a> Lautsprecher für 30 Euro bei Aldi kaufen:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/medion-md-83962.jpg" class="image"><img src="//martin-thoma.com/captions/medion-md-83962.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Medion MD 83962</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/medion-md-83962-anschluesse.jpg" class="image"><img src="//martin-thoma.com/captions/medion-md-83962-anschluesse.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Medion MD 83962: Anschlüsse</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/medion-md-83962-micro-netzteil.jpg" class="image"><img src="//martin-thoma.com/captions/medion-md-83962-micro-netzteil.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Medion MD 83962: Micro-USB Netzteil</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/medion-md-83962-micro-usb.jpg" class="image"><img src="//martin-thoma.com/captions/medion-md-83962-micro-usb.jpg" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Medion MD 83962: Micro-USB auf USB Anschluss</div></div></li></ul> <p>Ich habe sie mir angeschaut, bin aber enttäuscht. Wenn ich sie per Bluetooth an mein Nexus 4 anschließe gibt es hässliche Geräusche von sich. Außerdem ist die Audio-Qualität nicht so toll und die Freisprechfunktion ist … naja. Deutlich schechter als das interne Micro, wenn ich direkt zur Box rede.</p> <p>Um euch mal einen Vergleich zu geben, habe ich die ersten zwei Minuten des Open Movie “Bick Buck Bunny” mit meinem Nexus 4 aufgenommen. Bei der ersten Aufnahme hört man die erste 2 Minuten durch meine internen Notebook-Lautsprecher, bei der zweiten durch den Medion Life MD 83962 Lautsprecher (per Kabel mit dem Notebook verunden):</p> <ul> <li><a href="../images/2013/07/medion-md-83962.wav">Medion MD 83962: Bluetooth speakers</a></li> <li><a href="../images/2013/07/acer-travelmate-5744z.wav">Acer Travelmate 5744Z: Internal Speakers</a></li> </ul> <p>Hier hört man keinen großen Unterschied. Aber die internen Lautsprecher meines Acer Travelmate 5744Z hören sich besser an als der Bluetooth-Lautsprecher. Und das Micro ist wie gesagt ziemlich schlecht. Ich kann also definitiv keine Kaufempfehlung geben.</p> <p>Die Maße sind übrigens: 16,5 cm x 7,0 cm x 7,3 cm (Breite x Tiefe x Höhe).</p> Data Backup Strategies //martin-thoma.com/data-backup-strategies/ Mon, 08 Jul 2013 08:48:50 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/data-backup-strategies <p>Yesterday, I thought what would happen if my internal or external hard drive crashed.</p> <p>The hard disk of this computer contains 53 GB of data (on Linux: <code>df -H</code>). As my home folder only contains 35.3 GB of data, 17.7 GB seem to be programs. 21.1 GB the remaining data is for movies and 6.1 GB are for programming (and backed up via GitHub). Hence the by far biggest part of the lost data would be movies, the rest would be scattered across my home folder.</p> <p>The situation is similar for my external hard drive: A lot of video files, some audio files, A LOT of pictures and many, many miscellaneous files. I don’t want to lose data, but I don’t use my external HDD often. Most of the time I only have to do a <abbr title="regular expression">RegEx</abbr> search for file names (sometimes also a full text search for some files I found via RegEx) just to find out that the file I’m looking for is not there.</p> <h2>Online Services</h2> <p>I want to back up one computer with at least 200 GB which I don’t need to access often and 10 GB that need to access often.</p> <p>A backup service should include software, that …</p> <ul> <li>... allows me to configurate upload / dowload bandwidth limts</li> <li>... should integrate into my <abbr title="operating system">os</abbr> in such a way that it feels like using a hard disk</li> <li>... lets me upload files of sizes up to 5 GB</li> <li>... uploads in background automatically as soon as my notebook gets an internet connection</li> <li>... uploads only parts of files, if only parts changed</li> <li>... starts uploading as soon as a file changed</li> <li>... creates checksums and compares them to check if files were correctly uploaded</li> </ul> <p>A version control would be great, but that’s a feature I don’t expect. Also a possibility to share content (single files with a code) would be great, but I don’t know if any of those services offers that.</p> <table> <tr> <th>Name</th> <th>Euro / Year</th> <th>&nbsp;</th> <th>Free trial</th> <th>Clients</th> <th>Information</th> </tr> <tr> <td><a href="http://www.backblaze.com/">Backblaze</a></td> <td style="text-align:right;"><a href="http://www.backblaze.com/de_DE/online-backup-about.html">37.06</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /></td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td><a href="http://en.wikipedia.org/wiki/Backblaze">Wiki</a></td> </tr> <tr> <td><a href="http://www.carbonite.com/">Carbonite</a></td> <td style="text-align:right;"><a href="http://www.carbonite.com/online-backup/pricing-plans">46.78</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td><a href="http://en.wikipedia.org/wiki/Carbonite_(online_backup)">Wiki</a></td> </tr> <tr> <td><a href="http://www.crashplan.com/">CrashPlan</a></td> <td style="text-align:right;"><a href="http://www.crashplan.com/consumer/compare.html">46.78</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/tux.png" alt="Tux - Icon" width="16" height="16" class="size-full wp-image-73301" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td><a href="http://en.wikipedia.org/wiki/Crashplan#CrashPlan">Wiki</a></td> </tr> <tr> <td><a href="https://www.idrive.com/index.html">IDrive</a></td> <td style="text-align:right;"><a href="https://www.idrive.com/pricing.htm">116.58</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/tux.png" alt="Tux - Icon" width="16" height="16" class="size-full wp-image-73301" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td>-</td> </tr> <tr> <td><a href="https://www.jungledisk.com/">Jungle Disk</a></td> <td style="text-align:right;"><a href="https://www.jungledisk.com/personal/desktop/pricing/">238.62</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /></td> <td><img src="../images/2013/07/tux.png" alt="Tux - Icon" width="16" height="16" class="size-full wp-image-73301" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> ?</td> <td><a href="http://en.wikipedia.org/wiki/Jungle_Disk">Wiki</a></td> </tr> <tr> <td><a href="http://www.mimedia.com/">MiMedia</a></td> <td style="text-align:right;"><a href="http://www.mimedia.com/more-space/">77.20</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td>? <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td><a href="http://en.wikipedia.org/wiki/MiMedia">Wiki</a></td> </tr> <tr> <td><a href="http://mozy.com/">Mozy</a></td> <td style="text-align:right;"><a href="http://mozy.com/home/pricing/">131.00</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td><a href="http://en.wikipedia.org/wiki/Mozy">Wiki</a></td> </tr> <tr> <td><a href="http://www.nomadesk.com">Nomadesk</a></td> <td style="text-align:right;"><a href="http://www.nomadesk.com/pricing/">93.57</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /></td> <td>-</td> </tr> <tr> <td><a href="https://www.sugarsync.com/">SugarSync</a></td> <td style="text-align:right;"><a href="https://www.sugarsync.com/plans/">194.94</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /> <img src="../images/2013/07/windows-icon.png" alt="Windows icon" width="16" height="16" class="size-full wp-image-73321" /> <img src="../images/2013/07/mac-icon.png" alt="Mac - Icon" width="16" height="16" class="size-full wp-image-73331" /></td> <td><a href="http://en.wikipedia.org/wiki/SugarSync">Wiki</a></td> </tr> <tr> <td><a href="https://one.ubuntu.com/">Ubuntu One</a></td> <td style="text-align:right;"><a href="https://one.ubuntu.com/services/">187.09</a></td> <td>&nbsp;</td> <td><img src="../images/2013/07/accept.png" alt="accept icon" width="16" height="16" class="size-full wp-image-73351" /></td> <td><img src="../images/2013/07/tux.png" alt="Tux - Icon" width="16" height="16" class="size-full wp-image-73301" /> <img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /> <img src="../images/2013/07/cancel.png" alt="cancel" width="16" height="16" class="alignnone size-full wp-image-73371" /></td> <td><a href="http://en.wikipedia.org/wiki/Ubuntu_One">Wiki</a></td> </tr> </table> <p>I was a little bit surprised that there seems no way to use Google Drive as backup option (at least on Linux as there is <a href="http://www.change.org/en-GB/petitions/google-create-a-native-linux-google-drive-application">this petition</a> which was signed by 16,774 people).</p> <p>What could go wrong?</p> <ul> <li>A <abbr title="Denial of service"><a href="http://en.wikipedia.org/wiki/Denial-of-service_attack">DOS</a></abbr> attack against one of those companies might lead to temporarily unavailable services.</li> <li>Financial problems, bad backup techniques or personal mistakes might lead to permanent loss of data.</li> <li>Information might get leaked to the public.</li> <li>Information might get leaked to government (<a href="http://en.wikipedia.org/wiki/PRISM_(surveillance_program)">PRISM</a>, <a href="http://en.wikipedia.org/wiki/Tempora">Tempora</a>)</li> <li>You might get analyzed by the company that stores your data. They could create a personal profile and sell that (maybe not even on the content you use, but perhaps only with filenames and edit times)</li> <li>The software you've installed for your backup might be a malware.</li> <li>The software you've installed might have security issues that allow attackers to execute malware.</li> </ul> <h2>Offline</h2> <h3>RAID</h3> <p>All <a href="http://en.wikipedia.org/wiki/RAID">RAID</a> levels (except for RAID 0) offer redundancy. This means, they store data on more than one hard disk. This way, you can restore data after on (or if maybe more) hard disk crashes. But this is by no mean a guarantee that your data is secure.</p> <p>It’s recommended to use RAID with a RAID controller (a dedicated piece of hardware). Otherwise, you need some software that does it and your CPU time gets wasted with these operations.</p> <p>What could go wrong:</p> <ul> <li>One disk fails. You buy a new one to get security back, the RAID controller copies information to the new disk that replaced the crashed one. While it copies, the other disk gets heavy load. This heavy load might lead to another crash. Boom. Your data is lost.</li> <li>Your computer might get damaged (e.g. by a fire, by an earthquake, by overvoltage, by a cup of tea you accidentally threw over it, by an <a href="http://www.youtube.com/watch?v=HtTUsOKjWyQ">act of agression</a>)</li> <li>A burglar would probably steal all hardware you have at home.</li> </ul> <p>But RAID is no option for me as I use a notebook as my main computer.</p> <h3>External HDD</h3> <p>A very easy way to secure your files is an external hard disk drive. You can choose by yourself what and when to save your files for redundancy. But as I know myself, I will make those backups less often after a while. So I guess this will not work for me.</p> <p>You could probably also make an external HDD raid.</p> <h2>More possibilities</h2> <ul> <li><a href="http://aws.amazon.com/de/s3/#pricing">Amazon S3 Glacier</a> for 15.44 Euro/year or Amazon S3 Standard for 133.34 Euro/year e.g. with <a href="http://www.dragondisk.com/">DragonDisk</a> and <a href="http://ijaar.com/amazon-s3-tools/">others</a> - transactions are not included!</li> <li>Give external hard disks to friends / to bank.</li> <li>Software: <ul> <li><a href="http://en.wikipedia.org/wiki/Rsync">rsync</a> for Linux</li> <li><a href="http://en.wikipedia.org/wiki/Time_Machine_(Mac_OS)">Time machine</a> for Mac</li> </ul> </li> </ul> <h2>See also</h2> <ul> <li><a href="http://www.marco.org/2010/11/20/instapapers-backup-method">Instapaper&rsquo;s backup method</a></li> </ul> Improve German Public Transportation //martin-thoma.com/improve-german-public-transportation/ Sat, 06 Jul 2013 20:45:32 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/improve-german-public-transportation <p>Public transportation in Germany is much worse than it could be. I’ve got quite angry today because of that and thought about ways to improve the situation.</p> <p><strong>A story from today:</strong> I’ve bought two tickets to get from Karlsruhe to Augsburg (230 km) in about a month. I wanted to visit my dad in summer break just after an exam. I’ve bought a fixed connection to get there for “only” 35 Euro instead of 59 Euro. But I’ve made a mistake, my conenction started to early. Two hours after having bought the tickets, I wanted to exchange them for a connection that starts later. But I had to pay 15 Euro for exchanging them, 15 Euro for canceling the connection. And it got worse: I had to give them my home address to get at least some of the money back. For what the hell do they need my home address?</p> <h2>What could get improved?</h2> <ul> <li>Most people basically choose one company: <a href="http://en.wikipedia.org/wiki/Deutsche_Bahn">Deutsche Bahn</a></li> <li>It's too expensive.</li> <li>Customer service of "Deutsche Bahn" is very bad.</li> <li>Delays of at least 10 minutes always happen VERY often, delays of more than 30 minutes happen from time to time; I already had delay of more than 2 hours.</li> </ul> <h2>Alternative companies</h2> <p>Most people choose “Deutsche Bahn” (short: DB) because it is the biggest company that provides public transportation when you want to travel between cities. DB is well known and connects all big cities. However, there are alternatives.</p> <p>After a law (§ 13 Abs. 2 of the <a href="http://de.wikipedia.org/wiki/Personenbef%C3%B6rderungsgesetz_(Deutschland)">Personenbeförderungsgesetz</a>) was annulled, bus companies provided alternatives to traveling by train. Some companies are:</p> <ul> <li><a href="http://meinfernbus.de/">MeinFernbus.de</a></li> <li><a href="http://www.univers-reisen.de/">univers-reisen.de</a></li> <li><a href="http://www.city2city.de/">City2City.de</a></li> </ul> <p>But they are difficult to find and people maybe don’t trust in them.</p> <h2>Informing people</h2> <p><a href="https://www.google.com/intl/de/landing/transit/#dmy">Google Transit</a>, <a href="https://www.fahrtenfuchs.de/">FahrtenFuchs.de</a> and <a href="http://www.busliniensuche.de/">Busliniensuche.de</a> provide one possibility to inform people. But they all seem to have only a few bus companies.</p> <p>Google Transit is interesting as they provide <a href="https://developers.google.com/transit/gtfs/reference?hl=en">format specification</a> for exchanging transit information.</p> <h2>What could be done</h2> <ul> <li>Contact bus companies and ask them if they want to provide transit information to the public in Google Transit Feed Format. You might want to hint them to <a href="http://maps.google.com/help/maps/mapcontent/transit/index.html">Google Transit Partner Program</a>. <ul> <li>I've contacted "meinfernbus.de" (Saturday, 06.07.2013). Lets see if they answer.</li> <li>Contacted "KVV.de" (Saturday, 06.07.2013)</li> <li>Contacted "avv-augsburg.de" (Saturday, 06.07.2013)</li> </ul> </li> <li>Write software that allows bus companies to get their data into Google Transit Format <ol> <li>Write standard relational SQL database to store the required information</li> <li>Create <abbr title="user interface">UI</abbr> scribbles (e.g. with <a href="../how-can-i-sketch-an-application/" title="How can I sketch an application?">Balsamiq</a>)</li> <li>Write software</li> </ol> </li> </ul> <h2>Some reactions</h2> <h3>AVV (Augsburg)</h3> <p>My email from 06.07.2013 to kundencenter@avv-augsburg.de:</p> <blockquote>Sehr geehrte Damen und Herren, ich habe gerade gesehen, dass Google die M&ouml;glichkeit anbietet, die Fahrplaninformationen in Google Maps einzubinden: http://maps.google.com/help/maps/mapcontent/transit/index.html K&ouml;nnten Sie das anbieten? Es ist vermutlich deutlich einfacher, die Fahrplanauskunft von Google zu nutzen als auf die AVV-Seite zu gehen. Mit freundlichen Gr&uuml;&szlig;en, Martin Thoma</blockquote> <p>No reaction by now (21.07.2013)</p> <h3>KVV (Karlsruhe)</h3> <p>They have called me on 07.07.2013 and told me that they plan to bring the information to Google Maps, although they don’t know how long it will take.</p> <h3>MeinFernbus.de</h3> <p>My email from 06.07.2013:</p> <blockquote>Sehr geehrte Damen und Herren, ich habe mich heute sehr &uuml;ber die Deutsche Bahn ge&auml;rgert und auf der Suche nach Alternativen meinfernbus.de gefunden. Allerdings habe ich zuerst &uuml;ber Google Maps nach Busverbindungen zwischen Karlsruhe und Augsburg gesucht, wo mir leider nur die Bahn angeboten wurde. Haben Sie schon von Google Transit&lt;http://maps.google.com/help/maps/mapcontent/transit/index.html&gt;geh&ouml;rt? Was halten Sie davon, an diesem Programm teilzunehmen? Mit freundlichen Gr&uuml;&szlig;en, Martin Thoma</blockquote> <p>Answer from 08.07.2013:</p> <blockquote>Sehr geehrter Herr Thoma, bitte entschuldigen Sie die sp&auml;te Antwort. Vielen Dank f&uuml;r Ihre Email, Ihre Kooperationsanfrage ist bei uns eingegangen. Wir freuen uns sehr, dass Sie mit MeinFernbus.de, dem Marktf&uuml;hrer im deutschen Fernbusverkehr, zusammenarbeiten m&ouml;chten. Wir pr&uuml;fen gerne eine entsprechende Zusammenarbeit. Zu gegebener Zeit setzt sich unser Kooperationsmanager mit Ihnen in Verbindung. Aufgrund der Vielzahl eingehender Anfragen bitten wir Sie zun&auml;chst noch um etwas Geduld. Vielen Dank f&uuml;r Ihr Verst&auml;ndnis, herzliche Gr&uuml;&szlig;e aus der Hauptstadt Friederike Freytag</blockquote> <h2>See also</h2> <ul> <li><a href="http://www.youtube.com/watch?v=j6dCCq0XL6w">Reisetagebuch</a> (A German comedian)</li> </ul> Graphic filters //martin-thoma.com/graphic-filters/ Thu, 04 Jul 2013 18:21:19 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/graphic-filters <p>I begin to fall in love with JavaScript and HTML5. You can access your Webcam with JS! As an example, I’ve implemented some graphic filters.</p> <h2>Basics</h2> <h3>HTML5</h3> <p>You need:</p> <ul> <li><a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/canvas"><canvas> <li><a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/video"><video> This is the bare minimum HTML code you need for valid HTML: ```html &lt;!DOCTYPE html&gt; <html> <head> <title>Some title</title> </head> <body> <video autoplay="" id="vid" style="display:none;"></video> <canvas id="canvas" width="640" height="480"></canvas> <script type="text/javascript" src="graphic-filter.js"> </script> </body> </html> ``` <h3>JavaScript</h3> Important functions / datastructures are: <ul> <li><a href="https://developer.mozilla.org/en-US/docs/WebRTC/navigator.getUserMedia">getUserMedia</a>: see <a href="http://caniuse.com/stream">support by browsers</a></li> <li><a href="https://developer.mozilla.org/en-US/docs/Web/API/ImageData">ImageData</a>: WTF? The image is a ONE dimensional array of integers in 0, ..., 255. So the first 4 array elements describe the pixel (0|0) with its RGBA value</li> </ul> A starting point for your code might be: ```javascript 'use strict'; var video = document.querySelector("#vid"); var canvas = document.querySelector('#canvas'); var context = canvas.getContext('2d'); var localMediaStream = null; var onCameraFail = function (e) { console.log('Camera did not work.', e); }; setInterval(function snapshot() { if (localMediaStream) { context.drawImage(video, 0, 0); var width = 640; var height = 480; var imgDataNormal = context.getImageData(0, 0, width, height); var imgData = context.createImageData(width, height); // convert image to grayscale for (var i = 0; i &lt; imgData.width*imgData.height*4; i += 4) { var r = imgDataNormal.data[i + 0]; var g = imgDataNormal.data[i + 1]; var b = imgDataNormal.data[i + 2]; var brightness = (3*r+4*g+b)&gt;&gt;&gt;3; imgData.data[i] = brightness; imgData.data[i+1] = brightness; imgData.data[i+2] = brightness; } context.putImageData(imgData, 0, 0); } }, 500); navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia; window.URL = window.URL || window.webkitURL; navigator.getUserMedia({video:true}, function (stream) { video.src = window.URL.createObjectURL(stream); localMediaStream = stream; }, onCameraFail); console.log(localMediaStream); ``` <h2>Interactive example</h2> <div class="info"> You need a webcam for this: <a href="../html5/graphic-filters/graphic-filters.htm" target="_blank">Open demonstration in new window</a> </div> This is what it should look like: <div style="width: 674px" class="wp-caption aligncenter"><a href="../images/2013/07/graphic-webcam-html5-js-example.png"><img src="../images/2013/07/graphic-webcam-html5-js-example.png" alt="Webcam example" width="" height="" class="size-full wp-image-72801" /></a><p class="wp-caption-text">Webcam example</p></div> And it gives these results: <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/prewitt-x-filter-example.png" class="image"><img src="//martin-thoma.com/captions/prewitt-x-filter-example.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Prewitt x-filter example</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/prewitt-y-filter-example.png" class="image"><img src="//martin-thoma.com/captions/prewitt-y-filter-example.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Prewitt y-filter example</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/07/laplace-filter-example.png" class="image"><img src="//martin-thoma.com/captions/laplace-filter-example.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Laplace filter example</div></div></li></ul> By the way, you can check if a website is currently accessing your webcam (with Google Chrome): <div style="width: 380px" class="wp-caption aligncenter"><a href="../images/2013/07/webcam-red-dot.png"><img src="../images/2013/07/webcam-red-dot.png" alt="Webcam indicator on tab in Google Chrome" width="" height="" class="size-full wp-image-72811" /></a><p class="wp-caption-text">Webcam indicator on tab in Google Chrome</p></div> If you want to use these examples from your Android phone, you might have to enable getUserMedia. To do this, enable "Web RTC" in "chrome://flags": <div style="width: 190px" class="wp-caption aligncenter"><a href="../images/2013/07/enable-webrtc-180x300.png"><img src="../images/2013/07/enable-webrtc-180x300.png" alt="Enamble Web-RTC in Chrome for Android" width="" height="" class="size-medium wp-image-73191" /></a><p class="wp-caption-text">Enamble Web-RTC in Chrome for Android</p></div> </video></a></li></canvas></a></li></ul> three.js is AWESOME! //martin-thoma.com/three-js-is-awesome/ Mon, 01 Jul 2013 16:21:44 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/three-js-is-awesome <p>I recently discovered <a href="http://en.wikipedia.org/wiki/Three.js">three.js</a>, a JavaScript library/API used to create and display animated 3D computer graphics.</p> <p>Here are some examples what you can do with three.js. It’s pure JavaScript, no Flash required!</p> <p>They all worked smooth on my Notebook (<a href="http://ark.intel.com/products/50176/Intel-Pentium-Processor-P6200-3M-Cache-2_13-GHz">Intel Pentium P6200</a> processor) with Google Chrome 28 on Linux.</p> <div class="info">You have to click on the links to see the examples!</div> <h2>Stemkoski</h2> <h3>Textures</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/threejs-textures.png"><img src="../images/2013/07/threejs-textures.png" alt="Three.js textures example" width="" height="" class="size-full wp-image-72431" /></a><p class="wp-caption-text">Three.js textures example</p></div> <p><a href="http://stemkoski.github.io/Three.js/Textures.html">Demonstration</a></p> <h3>Three.js</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/threejs-skybox.png"><img src="../images/2013/07/threejs-skybox.png" alt="Threejs Skybox example" width="" height="" class="size-full wp-image-72441" /></a><p class="wp-caption-text">Threejs Skybox example</p></div> <p><a href="http://stemkoski.github.io/Three.js/Skybox.html">Demonstration</a></p> <h3>Reflection</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/threejs-reflection.png"><img src="../images/2013/07/threejs-reflection.png" alt="Reflection example" width="" height="" class="size-full wp-image-72451" /></a><p class="wp-caption-text">Reflection example</p></div> <p><a href="http://stemkoski.github.io/Three.js/Reflection.html">Demonstration</a></p> <h3>Webcam</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/threejs-webcam.png"><img src="../images/2013/07/threejs-webcam.png" alt="Webcam example" width="" height="" class="size-full wp-image-72461" /></a><p class="wp-caption-text">Webcam example</p></div> <p><a href="http://stemkoski.github.io/Three.js/Many-Cameras.html">Demonstration</a></p> <h3>Motion detection</h3> <div style="width: 566px" class="wp-caption aligncenter"><a href="../images/2013/07/threejs-motion.png"><img src="../images/2013/07/threejs-motion.png" alt="Motion detection with three.js!" width="" height="" class="size-full wp-image-72471" /></a><p class="wp-caption-text">Motion detection with three.js!</p></div> <p><a href="http://stemkoski.github.io/Three.js/Webcam-Motion-Detection.html">Demonstration</a></p> <h3>3D function plotter</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/threejs-3d-function.png"><img src="../images/2013/07/threejs-3d-function.png" alt="3D function plotter" width="" height="" class="size-full wp-image-72481" /></a><p class="wp-caption-text">3D function plotter</p></div> <p><a href="http://stemkoski.github.io/Three.js/Graphulus-Function.html">Demonstration</a></p> <h2>HexGL</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/se-oorr2zM8" frameborder="0" allowfullscreen=""></iframe> <p><a href="http://hexgl.bkcore.com/">Demonstration</a></p> <h2>Solar System</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/solar-system-simulation.png"><img src="../images/2013/07/solar-system-simulation.png" alt="Solar system simulation" width="" height="" class="size-full wp-image-72501" /></a><p class="wp-caption-text">Solar system simulation</p></div> <p><a href="http://www.webdev20.pl/skins/default/js/demos/solar_system/index.html">Demonstration</a></p> <h2>Planet Maker</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/07/PlanetMaker.png"><img src="../images/2013/07/PlanetMaker.png" alt="PlanetMaker" width="" height="" class="size-full wp-image-72521" /></a><p class="wp-caption-text">PlanetMaker</p></div> <p><a href="http://planetmaker.wthr.us/?model=51b8d1021fef93.32065956">Demonstration</a> - takes ages to load, but when its loaded it is fast</p> <h2>See also</h2> <ul> <li><a href="http://stemkoski.github.io/Three.js/">stemkoski</a>: Many examples</li> <li><a href="http://www.chromeexperiments.com/tag/3d/">Chrome Experiments</a></li> </ul> Music videos //martin-thoma.com/music-videos/ Sun, 30 Jun 2013 21:21:51 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/music-videos <h2>Paint: Lord of the Rings</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/3FPxYDGfniM" frameborder="0" allowfullscreen=""></iframe> <h2>Chatroulette Concert</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/LfamTmY5REw" frameborder="0" allowfullscreen=""></iframe> <h2>Chatroulette Love Song</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/fU1x8Ll62QE" frameborder="0" allowfullscreen=""></iframe> <h2>28 Cartoon Theme Songs in 7 Minutes</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/lRUHVFQxbE4" frameborder="0" allowfullscreen=""></iframe> <h2>Bodo Wartke - Da muss er durch</h2> <iframe width="512" height="288" src="//www.youtube.com/embed/vw_ECJKdNcE" frameborder="0" allowfullscreen=""></iframe> <ul> <li><a href="http://www.youtube.com/watch?v=ZOb0bErcDyg">Liebeslied</a> (In German, English, French, Spanish, Italian, Chinese, Russian, Turkish, Arabic, Bavarian, Swiss, Finnish)</li> <li><a href="http://www.youtube.com/watch?v=QpF0MRGwOQA">Believe in Steve</a></li> </ul> <h2>Atomic Theory Song</h2> <iframe width="512" height="384" src="//www.youtube.com/embed/07yDiELe83Y" frameborder="0" allowfullscreen=""></iframe> <h2>The 50 States Of The USA and The Capitals</h2> <iframe width="512" height="384" src="//www.youtube.com/embed/0ZhZhWnbkO8" frameborder="0" allowfullscreen=""></iframe> <p>(From television series “Animaniacs”)</p> <ul> <li><a href="http://www.youtube.com/watch?v=VyzQItUhXyw">Nations of the world</a></li> <li><a href="http://www.youtube.com/watch?v=f_J5rBxeTIk">Yakko's Universe Song</a></li> <li><a href="http://www.youtube.com/watch?v=s8eFFnJsCjs">The Planet Song</a></li> <li><a href="http://www.youtube.com/watch?v=EGMBUzFyVl4">Panama Canal</a></li> </ul> Spline interpolation //martin-thoma.com/spline-interpolation/ Sun, 30 Jun 2013 13:58:20 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/spline-interpolation <p>Just like before with polynomial interpolation, we have a list of <code>$n+1$</code> given point <code>$(x_i, y_i)$</code> with <code>$x_0 &lt; x_1 &lt; \dots &lt; x_n$</code>.</p> <p>We want to find a function that goes through those points and approximates the underlying function that produced that points as good as possible.</p> <h2>Polynomial interpolation</h2> <p>The problem of polynomial interpolation were oscillations at the end of the interval you wanted to interpolate (see <a href="../html5/polynom-interpolation.htm?function=1%2F(25*x*x%2B1)&amp;evaluationSteps=0.01&amp;X_MIN=-1.5&amp;X_MAX=1.5&amp;Y_MAX=1.2&amp;Y_MIN=-1.2&amp;X_TICKS_STEPS=0.2&amp;Y_TICKS_STEPS=0.2&amp;X_FROM=-1&amp;X_TO=1&amp;N_EVALUATION_POINTS=10&amp;points=%5B%5D&amp;tschebyscheffSwitch=true&amp;equallySwitch=true">interactive example</a>):</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/06/polynomial-interpolation-oscillation-300x105.png"><img src="../images/2013/06/polynomial-interpolation-oscillation-300x105.png" alt="Oscillations you get with polynomial interpolation" width="" height="" class="size-medium wp-image-72001" /></a><p class="wp-caption-text">Oscillations you get with polynomial interpolation</p></div> <p>As you can see, polynomial interpolation with equally spaced points is very, very bad at the ends of the interval. Tschebyscheff spaced points are much better, but you can still see that the interpolated function is different from the original.</p> <h2>Splines</h2> <p>A way to solve this problem are splines. A spline is a piecewise-defined function that goes through some points (aka knots) and is smooth.</p> <p>More formally: Let <code>$s: [x_0,x_n] \rightarrow \mathbb{R}$</code> be a spline. Then:</p> <ol style="list-style-type: none;"> <li>(S1) <strong>cubic</strong>: `$\forall i \in \{1, \dots, n\}: s|_{x_{i-1}, x_i}$` is a cubic function</li> <li>(S2) <strong>interpolation</strong>: `$\forall i \in \{0, \dots, n\}: s(x_i) = y_i$`</li> <li>(S3) <strong>smooth</strong>: `$s \in C^2([x_0, x_n])$` and `$\int_{x_0}^{x_n} s''(x)^2 \mathrm{d}x$` is minimal</li> </ol> <p>When you use a cubic function <code>$a x^3 + b x^2 + cx + d$</code> for each of the <code>$n$</code> intervals that we got by our <code>$n+1$</code> points, you have <code>$4n$</code> variables that you need to calculate.</p> <p>Condition (S2) gives two equations per interval which makes <code>$2n$</code> equations of the form:</p> <p><code>$ \begin{align} y_i &amp;= a_i x_i^3 &amp;&amp;+ b_i x_i^2 &amp;&amp;+ c_i x_i &amp;&amp;+ d_i\\ y_{i+1} &amp;= a_i x_{i+1}^3 &amp;&amp;+ b_i x_{i+1}^2 &amp;&amp;+ c_i x_{i+1} &amp;&amp;+ d_i \end{align} $</code></p> <p>At first glance condition (S3) - <code>$s \in C^2([x_0, x_n])$</code> - seems to be redundant with (S1) - <code>$s$</code> is piecewise cubic. Every polynomial is in <code>$C^\infty(\mathbb{R})$</code>, so it certainly is in <code>$C^2([x_0, x_n])$</code>.<br /> That’s correct. But <code>$s$</code> is not a polynomial. It’s only piecewise-defined as a polynomial. That makes a difference at the ends of the intervals. And it gives us <code>$2n-2$</code> more equations:</p> <p><code>$\displaystyle \begin{align} s_i' (x_{i}) &amp;= s_{i+1}'(x_{i}) \;\;\; &amp;&amp;\forall i=1, \dots, n-1\\ s_i''(x_{i}) &amp;= s_{i+1}''(x_{i}) \;\;\; &amp;&amp;\forall i=1, \dots, n-1 \end{align} $</code></p> <p>which is equivalent to</p> <p><code>$\displaystyle \begin{align} 3a_i x_i^2 + 2b_i x_i + c_i &amp;= 3a_{i+1} x_i^2 + 2b_{i+1} x_i + c_{i+1} \;\;\; &amp;&amp;\forall i=1, \dots, n-1\\ 6a_i x_i + 2b_i &amp;= 6a_{i+1} x_i + 2b_{i+1} \;\;\; &amp;&amp;\forall i=1, \dots, n-1 \end{align} $</code></p> <p>All equations we have are linear. Please note that the variables we want to determine are <code>$a_i, b_i, c_i, d_i$</code>. So <code>$x_i^3$</code> is simply a multiplicative constant that we have to evaluate before we solve our system of equations.</p> <p>But at the moment, we only have <code>$2n+2\cdot(n-1) = 4n -2$</code> equations, but we have <code>$4n$</code> variables. So we need ancillary conditions to solve this linear system of equations.</p> <h2>Possible ancillary conditions</h2> <ul> <li><strong>natural splines</strong>: `$s''(x_0) =0, \;\;\; s''(x_n) = 0$`</li> <li><strong>clamped splines</strong>: `$s'(x_0) = f'(x_0),\;\;\; s'(x_n)= f'(x_n)$` where `$y_0'$` and `$y_n'$` can be any value</li> <li><strong>periodic</strong>: `$s'(x_0) = s'(x_n), \;\;\; s''(x_0) = s''(x_n)$`</li> <li><strong>not-a-knot</strong>: `$s_1''' = s_2''', \;\;\; s_{n-1}''' = s_{n}'''$`</li> </ul> <p>George MacKerron shows how the results can differ in his article <a href="http://blog.mackerron.com/2011/01/01/javascript-cubic-splines/">Cubic splines in JavaScript (via CoffeeScript)</a>:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/06/ancillary-conditions-splines-results.png"><img src="../images/2013/06/ancillary-conditions-splines-results.png" alt="Different results for different ancillary conditions" width="" height="" class="size-full wp-image-72221" /></a><p class="wp-caption-text">Different results for different ancillary conditions</p></div> <h2>Code for natural splines</h2> <p>I will store splines as a list of maps. Each map is one piece of the spline and has:</p> <ul> <li>`$u$`: Start of the interval</li> <li>`$v$`: End of the interval</li> <li>`$a,b,c,d$`: cubic function `$ax^3 + bx^2 + cx +d$`</li> </ul> <p>Please note that I didn’t test the code below. It’s likely that there are errors with indices.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">niceCubicPolynomial</span><span class="p">(</span><span class="n">p</span><span class="p">):</span> <span class="n">tmp</span> <span class="o">=</span> <span class="s">&quot;&quot;</span> <span class="k">if</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;a&quot;</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot; x^3&quot;</span> <span class="k">elif</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;a&quot;</span><span class="p">]</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="si">%.2f</span><span class="s">x^3&quot;</span> <span class="o">%</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;a&quot;</span><span class="p">]</span> <span class="k">if</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;b&quot;</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">+ x^2&quot;</span> <span class="k">elif</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;b&quot;</span><span class="p">]</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">+ </span><span class="si">%.2f</span><span class="s">x^2&quot;</span> <span class="o">%</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;b&quot;</span><span class="p">]</span> <span class="k">else</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t\t</span><span class="s">&quot;</span> <span class="k">if</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;c&quot;</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">+ x&quot;</span> <span class="k">elif</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;c&quot;</span><span class="p">]</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">+ </span><span class="si">%.2f</span><span class="s">x&quot;</span> <span class="o">%</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;c&quot;</span><span class="p">]</span> <span class="k">else</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t\t</span><span class="s">&quot;</span> <span class="k">if</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;d&quot;</span><span class="p">]</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">+ </span><span class="si">%.2f</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;d&quot;</span><span class="p">]</span> <span class="k">return</span> <span class="n">tmp</span> <span class="k">def</span> <span class="nf">getSpline</span><span class="p">(</span><span class="n">points</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; points should be a list of maps, </span> <span class="sd"> where each map represents a point and has &quot;x&quot; and &quot;y&quot; &quot;&quot;&quot;</span> <span class="kn">import</span> <span class="nn">numpy</span><span class="o">,</span> <span class="nn">scipy.linalg</span> <span class="c"># sort points by x value</span> <span class="n">points</span> <span class="o">=</span> <span class="nb">sorted</span><span class="p">(</span><span class="n">points</span><span class="p">,</span> <span class="n">key</span><span class="o">=</span><span class="k">lambda</span> <span class="n">point</span><span class="p">:</span> <span class="n">point</span><span class="p">[</span><span class="s">&quot;x&quot;</span><span class="p">])</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">points</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span> <span class="c"># Set up a system of equations of form Ax=b</span> <span class="n">A</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">zeros</span><span class="p">(</span><span class="n">shape</span><span class="o">=</span><span class="p">(</span><span class="mi">4</span><span class="o">*</span><span class="n">n</span><span class="p">,</span><span class="mi">4</span><span class="o">*</span><span class="n">n</span><span class="p">))</span> <span class="n">b</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">zeros</span><span class="p">(</span><span class="n">shape</span><span class="o">=</span><span class="p">(</span><span class="mi">4</span><span class="o">*</span><span class="n">n</span><span class="p">,</span><span class="mi">1</span><span class="p">))</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="c"># 2n equations from condtions (S2)</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">**</span><span class="mi">3</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">**</span><span class="mi">2</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">2</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">3</span><span class="p">]</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">b</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;y&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">**</span><span class="mi">3</span> <span class="n">A</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">**</span><span class="mi">2</span> <span class="n">A</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">2</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">3</span><span class="p">]</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">b</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;y&quot;</span><span class="p">]</span> <span class="c"># 2n-2 equations for (S3):</span> <span class="k">if</span> <span class="n">i</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">continue</span> <span class="c"># point i is an inner point</span> <span class="n">A</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="mi">3</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">**</span><span class="mi">2</span> <span class="n">A</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="mi">2</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">2</span><span class="p">]</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">A</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">0</span><span class="o">+</span><span class="mi">4</span><span class="p">]</span> <span class="o">=</span> <span class="o">-</span><span class="mi">3</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">**</span><span class="mi">2</span> <span class="n">A</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="o">+</span><span class="mi">4</span><span class="p">]</span> <span class="o">=</span> <span class="o">-</span><span class="mi">2</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">2</span><span class="o">+</span><span class="mi">4</span><span class="p">]</span> <span class="o">=</span> <span class="o">-</span><span class="mi">1</span> <span class="n">b</span><span class="p">[</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)]</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="mi">6</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="mi">2</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">0</span><span class="o">+</span><span class="mi">4</span><span class="p">]</span> <span class="o">=</span> <span class="o">-</span><span class="mi">6</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="o">+</span><span class="mi">4</span><span class="p">]</span> <span class="o">=</span> <span class="o">-</span><span class="mi">2</span> <span class="n">b</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">)]</span> <span class="o">=</span> <span class="mi">0</span> <span class="c"># Natural spline:</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="o">+</span><span class="mi">0</span><span class="p">][</span><span class="mi">0</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">6</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="mi">0</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="o">+</span><span class="mi">0</span><span class="p">][</span><span class="mi">0</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">2</span> <span class="n">b</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">0</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">0</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">6</span><span class="o">*</span><span class="n">points</span><span class="p">[</span><span class="n">n</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="mi">4</span><span class="o">*</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">2</span> <span class="n">b</span><span class="p">[</span><span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">0</span> <span class="n">x</span> <span class="o">=</span> <span class="n">scipy</span><span class="o">.</span><span class="n">linalg</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="n">spline</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">spline</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;u&quot;</span><span class="p">:</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">],</span> <span class="s">&quot;v&quot;</span><span class="p">:</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">],</span> <span class="s">&quot;a&quot;</span><span class="p">:</span> <span class="nb">float</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">0</span><span class="p">]),</span> <span class="s">&quot;b&quot;</span><span class="p">:</span> <span class="nb">float</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">]),</span> <span class="s">&quot;c&quot;</span><span class="p">:</span> <span class="nb">float</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">2</span><span class="p">]),</span> <span class="s">&quot;d&quot;</span><span class="p">:</span> <span class="nb">float</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="mi">4</span><span class="o">*</span><span class="n">i</span><span class="o">+</span><span class="mi">3</span><span class="p">])})</span> <span class="k">return</span> <span class="n">spline</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">points</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="mf">0.0</span><span class="p">,</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="o">-</span><span class="mi">4</span><span class="p">})</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="mf">1.0</span><span class="p">,</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="mi">9</span><span class="p">})</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="mf">2.0</span><span class="p">,</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="mi">35</span><span class="p">})</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="mf">3.0</span><span class="p">,</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="mi">70</span><span class="p">})</span> <span class="n">spline</span> <span class="o">=</span> <span class="n">getSpline</span><span class="p">(</span><span class="n">points</span><span class="p">)</span> <span class="k">for</span> <span class="n">p</span> <span class="ow">in</span> <span class="n">spline</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">=</span> <span class="s">&quot;[</span><span class="si">%.2f</span><span class="s">, </span><span class="si">%.2f</span><span class="s">]:&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">p</span><span class="p">[</span><span class="s">&quot;u&quot;</span><span class="p">],</span> <span class="n">p</span><span class="p">[</span><span class="s">&quot;v&quot;</span><span class="p">])</span> <span class="n">tmp</span> <span class="o">+=</span> <span class="n">niceCubicPolynomial</span><span class="p">(</span><span class="n">p</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">tmp</span><span class="p">)</span></code></pre></div> <h2>See also</h2> <ul> <li><a href="http://math.stackexchange.com/q/430141/6876">How do the different ancillary conditions for splines differ?</a></li> </ul> Zero Mean Normalized Cross-Correlation //martin-thoma.com/zero-mean-normalized-cross-correlation/ Fri, 28 Jun 2013 22:15:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/zero-mean-normalized-cross-correlation <div style="width: 138px" class="wp-caption alignright"><a href="../images/2013/06/image-correlation.png"><img src="../images/2013/06/image-correlation.png" alt="Image correlation test image" width="" height="" class="size-full wp-image-71931" /></a><p class="wp-caption-text">An image from Tsukuba University. This is one of hundreds of images that you can use to test your algorithms. Link is below.</p></div> <p>Zero Mean Normalized Cross-Correlation or shorter ZNCC is an integer you can get when you compare two grayscale images.</p> <p>Lets say you have a webcam at a fixed position for security. It takes images all the time, but most of the time the room is empty. So quite a lot of images will not be interesting. They only waste space. So you want to get rid of those redundant images.</p> <p>BUT those images are not identical! Even if the scenery didn’t change, your sensor will produce slightly different results. A human will not notice them, but you can’t simply compare images bit by bit. Even if you could, the images will be different because the sun moved (and so do shadows) and perhaps you have a clock in the image.</p> <p>Now you can solve this problem with various techniques.</p> <p>I want to describe those techniques in a very general way. As the images in other scenarios might have different sizes and you probably don’t want to compare whole images, I’ll assume you have a part of both image of size <code>$(2n+1) \times (2n+1)$</code>. The pixel in the center has coordinates <code>$(u_1, v_1)$</code> for the part of the first image and <code>$(u_2, v_2)$</code> for the second image.</p> <h2>Sum of squared differences</h2> <p>Go through all pixels, get the difference of both and add up the squares:</p> <p><code>$\displaystyle SSD(Img_1, Img_2, u_1, v_1, u_2, v_2, n) := \sum_{i=-n}^n \sum_{j=-n}^n \left ( Img_1(u_1+i, v_1+j) - Img_2(u_2 + i, v_2 + j) \right )^2$</code></p> <p>When SSD is small, both images are very similar. Wehn SSD is 0, the images are identical.</p> <h2>Zero Mean Normalized Cross-Correlation</h2> <p>The average gray value is: <code>$\displaystyle \overline{Img}(u, v, n) := \frac{1}{(2n+1)^2} \sum_{i=-n}^n \sum_{j=-n}^n Img(u+i, v+j)$</code></p> <p>The standard deviation is: <code>$\displaystyle \sigma(u, v, n) := \sqrt{\frac{1}{(2n+1)^2} \left (\sum_{i=-n} \sum_{j=-n}^n (Img(u +i, v+j)-\overline{Img}(u, v, n))^2 \right )}$</code></p> <p>The ZNCC is defined as:</p> <p><code>$\displaystyle ZNCC(Img_1, Img_2, u_1, v_1, u_2, v_2, n) := \frac{\frac{1}{(2n+1)^2}\sum_{i=-n}^n \sum_{j=-n}^n \prod_{t=1}^2 \left (Img_t (u_t+i,v_t+j) - \overline{Img}(u_t, v_t, n) \right )}{\sigma_1(u_1, v_1, n) \cdot \sigma_2(u_2, v_2, n)}$</code></p> <p>The higher the ZNCC gets, the more are those two images correlated. (I think the value is always in [0, 1])</p> <p>Here is some Python code:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">getAverage</span><span class="p">(</span><span class="n">img</span><span class="p">,</span> <span class="n">u</span><span class="p">,</span> <span class="n">v</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;img as a square matrix of numbers&quot;&quot;&quot;</span> <span class="n">s</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="n">n</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="n">n</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">s</span> <span class="o">+=</span> <span class="n">img</span><span class="p">[</span><span class="n">u</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="n">v</span><span class="o">+</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="nb">float</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o">/</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">**</span><span class="mi">2</span> <span class="k">def</span> <span class="nf">getStandardDeviation</span><span class="p">(</span><span class="n">img</span><span class="p">,</span> <span class="n">u</span><span class="p">,</span> <span class="n">v</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">s</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">avg</span> <span class="o">=</span> <span class="n">getAverage</span><span class="p">(</span><span class="n">img</span><span class="p">,</span> <span class="n">u</span><span class="p">,</span> <span class="n">v</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="n">n</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="n">n</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">s</span> <span class="o">+=</span> <span class="p">(</span><span class="n">img</span><span class="p">[</span><span class="n">u</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="n">v</span><span class="o">+</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">avg</span><span class="p">)</span><span class="o">**</span><span class="mi">2</span> <span class="k">return</span> <span class="p">(</span><span class="n">s</span><span class="o">**</span><span class="mf">0.5</span><span class="p">)</span><span class="o">/</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="k">def</span> <span class="nf">zncc</span><span class="p">(</span><span class="n">img1</span><span class="p">,</span> <span class="n">img2</span><span class="p">,</span> <span class="n">u1</span><span class="p">,</span> <span class="n">v1</span><span class="p">,</span> <span class="n">u2</span><span class="p">,</span> <span class="n">v2</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">stdDeviation1</span> <span class="o">=</span> <span class="n">getStandardDeviation</span><span class="p">(</span><span class="n">img1</span><span class="p">,</span> <span class="n">u1</span><span class="p">,</span> <span class="n">v1</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="n">stdDeviation2</span> <span class="o">=</span> <span class="n">getStandardDeviation</span><span class="p">(</span><span class="n">img2</span><span class="p">,</span> <span class="n">u2</span><span class="p">,</span> <span class="n">v2</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="n">avg1</span> <span class="o">=</span> <span class="n">getAverage</span><span class="p">(</span><span class="n">img1</span><span class="p">,</span> <span class="n">u1</span><span class="p">,</span> <span class="n">v1</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="n">avg2</span> <span class="o">=</span> <span class="n">getAverage</span><span class="p">(</span><span class="n">img2</span><span class="p">,</span> <span class="n">u2</span><span class="p">,</span> <span class="n">v2</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="n">s</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="n">n</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="n">n</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">s</span> <span class="o">+=</span> <span class="p">(</span><span class="n">img1</span><span class="p">[</span><span class="n">u1</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="n">v1</span><span class="o">+</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">avg1</span><span class="p">)</span><span class="o">*</span><span class="p">(</span><span class="n">img2</span><span class="p">[</span><span class="n">u2</span><span class="o">+</span><span class="n">i</span><span class="p">][</span><span class="n">v2</span><span class="o">+</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">avg2</span><span class="p">)</span> <span class="k">return</span> <span class="nb">float</span><span class="p">(</span><span class="n">s</span><span class="p">)</span><span class="o">/</span><span class="p">((</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">**</span><span class="mi">2</span> <span class="o">*</span> <span class="n">stdDeviation1</span> <span class="o">*</span> <span class="n">stdDeviation2</span><span class="p">)</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">3</span><span class="p">],[</span><span class="mi">4</span><span class="p">,</span><span class="mi">5</span><span class="p">,</span><span class="mi">6</span><span class="p">],[</span><span class="mi">7</span><span class="p">,</span><span class="mi">8</span><span class="p">,</span><span class="mi">9</span><span class="p">]]</span> <span class="n">B1</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">3</span><span class="p">],[</span><span class="mi">4</span><span class="p">,</span><span class="mi">5</span><span class="p">,</span><span class="mi">6</span><span class="p">],[</span><span class="mi">7</span><span class="p">,</span><span class="mi">8</span><span class="p">,</span><span class="mi">9</span><span class="p">]]</span> <span class="n">B2</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">3</span><span class="p">],[</span><span class="mi">4</span><span class="p">,</span><span class="mi">5</span><span class="p">,</span><span class="mi">6</span><span class="p">],[</span><span class="mi">7</span><span class="p">,</span><span class="mi">8</span><span class="p">,</span><span class="mi">7</span><span class="p">]]</span> <span class="k">print</span><span class="p">(</span><span class="n">zncc</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">zncc</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B2</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">))</span></code></pre></div> <h2>See also</h2> <ul> <li><a href="http://www.site.uottawa.ca/research/viva/projects/imagepairs/">Feature point image matching</a></li> <li><a href="http://www.cvlab.cs.tsukuba.ac.jp/index.php?CVLAB%20Home%20Page">Tsukuba University stereo images</a>: Just in case you want to try those algorithms</li> <li><a href="http://siddhantahuja.wordpress.com/tag/normalized-cross-correlation/">Correlation based similarity measures-Summary</a></li> <li><a href="http://www.ti.uni-bielefeld.de/downloads/publications/diploma_theses/ba11_bboettcher_illuminationchange.pdf">Bachelorarbeit</a>: Bildvorverarbeitung und Bild&auml;hnlichkeitsfunktionen f&uuml;r beleuchtungstolerante visuelle Navigation (German)</li> </ul> JavaScript: WTF?!? //martin-thoma.com/javascript-wtf/ Wed, 26 Jun 2013 22:51:52 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/javascript-wtf <p>JavaScript is THE web programming language. It gets interpreted by your browser and web applications like Google Mail, Google Maps and Facebook make heavy use of them. Almost always, when you see something working smoothly / interactive, you see JavaScript in action.</p> <p>But JavaScript has a lot of “features” which are … well, I don’t have words for those. Just continue reading.</p> <p>Most of the following content is from a StackOverflow question <a href="http://stackoverflow.com/q/1995113/562769">Strangest language feature</a></p> <h2>Weak typing</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">3</span><span class="p">..</span><span class="nx">toString</span><span class="p">());</span></code></pre></div> <p><strong>Output</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="s1">&#39;3&#39;</span></code></pre></div> <p><strong>Explanation</strong> <strong>3.</strong> is a floating point and can get converted to a string. But <code>3.toString()</code> gives</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">SyntaxError: Unexpected token ILLEGAL</code></pre></div> <h2>Weak typing and string concatenation</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;5&#39;</span> <span class="o">+</span> <span class="mi">3</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;5&#39;</span> <span class="o">-</span> <span class="mi">3</span><span class="p">);</span></code></pre></div> <p><strong>Output</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="s1">&#39;53&#39;</span> 2</code></pre></div> <p><strong>Explanation</strong> JavaScript automatically converts datatypes and <code>+</code> is used for string concatenation and for addition.</p> <p>In the first case, as the first datatype is a string and <code>+</code> is defined for strings as concatenation, JS converts <code>3</code> to <code>'3'</code> which results in the string <code>'53'</code>.</p> <p>In the second case, <code>-</code> is only defined for subtraction so <code>'5'</code> gets converted to a number (int? float? I don’t know. I guess int.)</p> <h2>Automatic semicolons</h2> <p><strong>Example 1</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="kd">function</span> <span class="nx">test</span><span class="p">()</span> <span class="p">{</span> <span class="k">return</span> <span class="p">{</span> <span class="nx">id</span> <span class="o">:</span> <span class="mi">1338</span><span class="p">,</span> <span class="nx">title</span> <span class="o">:</span> <span class="s1">&#39;This is a test&#39;</span> <span class="p">};</span> <span class="p">}</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="nx">test</span><span class="p">());</span></code></pre></div> <p><strong>Example 2</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="kd">function</span> <span class="nx">test</span><span class="p">()</span> <span class="p">{</span> <span class="k">return</span> <span class="mi">2</span> <span class="o">+</span> <span class="mi">2</span><span class="p">;</span> <span class="p">}</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="nx">test</span><span class="p">());</span></code></pre></div> <p><strong>Output 1</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Uncaught SyntaxError: Unexpected token :</code></pre></div> <p><strong>Output 2</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">undefined</code></pre></div> <p><strong>Explanation</strong> JS adds a <code>;</code> at every line end. Automatically. You can’t prevent it.</p> <p>Please note that the second output is no error! It has a (valid) return value of <code>undefined</code>.</p> <h2>Truth table</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- 0 == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- false == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- &#39;&#39; == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- null == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- undefined == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- \t\r\n == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- &#39;0&#39; == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- &#39;false&#39; == XYZ ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;--------------------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == 0 ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">0</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="mi">0</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == false ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">false</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="kc">false</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == &#39;&#39; ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;&#39;</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="s1">&#39;&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == null ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">null</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="kc">null</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == undefined ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="kc">undefined</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="kc">undefined</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == \t\r\n ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot; \t\r\n&quot;</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="s2">&quot; \t\r\n&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == &#39;0&#39; ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;0&#39;</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="s1">&#39;0&#39;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s2">&quot;------- XYZ == &#39;false&#39; ---------&quot;</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="s1">&#39;false&#39;</span> <span class="o">==</span> <span class="s1">&#39;false&#39;</span><span class="p">);</span></code></pre></div> <p><strong>Output</strong></p> <table> <tr> <th>==</th> <th>0</th> <th>false</th> <th>''</th> <th>null</th> <th>undefined</th> <th>" \t\r\n"</th> <th>'0'</th> <th>'false'</th> </tr> <tr> <th>0</th> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> </tr> <tr> <th>false</th> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> </tr> <tr> <th>''</th> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> </tr> <tr> <th>null</th> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> </tr> <tr> <th>undefined</th> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> </tr> <tr> <th>" \t\r\n"</th> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> </tr> <tr> <th>'0'</th> <td style="background-color: lime;">true</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> <td style="background-color: red;">false</td> </tr> <tr> <th>'false'</th> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: red;">false</td> <td style="background-color: lime;">true</td> </tr> </table> <p><strong>Explanation</strong> Wow. This is fucked up. I’ve expected that strings compared to anything that is not the string itself evaluates to false.</p> <p>At least the table is symmetric and the diagonal is true. Please also note that JavaScript has a <code>===</code> operator.</p> <h2>The truth</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">2</span> <span class="o">==</span> <span class="p">[</span><span class="mi">2</span><span class="p">]);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">2</span> <span class="o">==</span> <span class="p">[[</span><span class="mi">2</span><span class="p">]]);</span></code></pre></div> <p><strong>Output</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">true</span> <span class="nb">true</span></code></pre></div> <p><strong>Explanation</strong> At <a href="http://stackoverflow.com/a/1724551/562769">StackOverflow</a></p> <h2>Date</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="kd">var</span> <span class="nx">futureDate</span> <span class="o">=</span> <span class="k">new</span> <span class="nb">Date</span><span class="p">(</span><span class="mi">2010</span><span class="p">,</span><span class="mi">77</span><span class="p">,</span><span class="mi">154</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="nx">futureDate</span><span class="p">);</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="nx">futureDate</span><span class="p">.</span><span class="nx">getYear</span><span class="p">());</span></code></pre></div> <p><strong>Output</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Tue Nov <span class="m">01</span> <span class="m">2016</span> 00:00:00 GMT+0100 <span class="o">(</span>CET<span class="o">)</span> 116</code></pre></div> <p><strong>Explanation</strong> 77 months and 154 days from the 0th day of 0th month of 2010</p> <p>You should use <code>getFullYear()</code> instead of <code>getYear()</code>, as the later one returns <code>year - 1900</code> (Why? When is this useful?)</p> <h2>Integer overflow</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="mi">111111111111111111111</span><span class="p">);</span></code></pre></div> <p><strong>Output</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">111111111111111110000</code></pre></div> <p><strong>Explanation</strong> It’s ok that JavaScript fails at handling this integer. I think it converts this to a float, but I’m not sure about that. But no matter what it does here, it doesn’t throw an error. That’s bad. How is a developer supposed to know in a big application know when something went wrong?</p> <h2>Function parameters</h2> <blockquote>In Javascript, declaring the parameters a function accepts is only a convenience to the programmer. All variables passed through the function call are accessible by the keyword <code>arguments</code>. So the following would alert "world": <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="kd">function</span> <span class="nx">blah</span><span class="p">(){</span> <span class="nx">alert</span><span class="p">(</span><span class="nx">arguments</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="p">}</span> <span class="nx">blah</span><span class="p">(</span><span class="s2">&quot;hello&quot;</span><span class="p">,</span> <span class="s2">&quot;world&quot;</span><span class="p">);</span></code></pre></div> </blockquote> <p><a href="http://stackoverflow.com/a/2023908/562769">Source</a> on StackOverflow</p> <h2>Global variables</h2> <p><strong>Example</strong></p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="kd">var</span> <span class="nx">a</span> <span class="o">=</span> <span class="mi">12</span><span class="p">;</span> <span class="kd">function</span> <span class="nx">test</span><span class="p">()</span> <span class="p">{</span> <span class="nx">a</span> <span class="o">=</span> <span class="mi">1337</span><span class="p">;</span> <span class="p">}</span> <span class="nx">test</span><span class="p">();</span> <span class="nx">console</span><span class="p">.</span><span class="nx">log</span><span class="p">(</span><span class="nx">a</span><span class="p">);</span></code></pre></div> <p><strong>Output</strong></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">1337</code></pre></div> <p><strong>Explanation</strong> When you forget to use <code>var</code> inside of <code>test()</code> you might accidentally use a global variable.</p> <h2>See also</h2> <p>Do you know some more JavaScript WTFs?</p> <p>You might also be interested in <a href="../php-a-strange-language/" title="PHP: A strange language">PHP: A strange language</a></p> Polynomial interpolation //martin-thoma.com/polynomial-interpolation/ Sat, 22 Jun 2013 18:41:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/polynomial-interpolation <p>Suppose you have a list of <code>$n+1$</code> given point <code>$(x_i, y_i)$</code> with <code>$i \in \{0, \dots, n\}$</code> and <code>$\forall i,j \in \{0, \dots, n\}: i \neq j \Rightarrow x_i \neq x_j$</code>.</p> <p>Now you want to find a polynomial <code>$\displaystyle p(x) = \sum_{i=0}^n a_i \cdot x^i$</code> that goes through all of the given points. This means:</p> <p><code>$\forall i \in \{0, \dots, n\}: p(x_i) = y_i$</code></p> <h2>Existence and uniqueness</h2> <p><strong>Theorem</strong>: When you have a list of <code>$n+1$</code> points with mutually different <code>$x_i$</code> there is exactly one polynom of degree <code>$\leq n$</code> that fits those points.</p> <p><strong>Proof</strong>:</p> <p>You can formulate a linear system of equations:</p> <p><code>$\underbrace{\begin{pmatrix} x_0^0 &amp; \cdots &amp; x_0^n \\ \vdots &amp; \ddots &amp; \vdots \\ x_n^0 &amp; \cdots &amp; x_n^n \end{pmatrix} }_{:= A \in \mathbb{R}^{(n+1) \times (n+1)}} \begin{pmatrix} a_0 \\ \vdots \\ a_n \end{pmatrix} = \begin{pmatrix} y_0 \\ \vdots \\ y_n \end{pmatrix}$</code></p> <p>A matrix of the form of <code>$A$</code> is called <a href="https://en.wikipedia.org/wiki/Vandermonde_matrix">Vandermonde matrix</a>. When the data points <code>$x_i$</code> are mutually different, it is known that the Vandermonde matrix is invertible (<a href="http://math.stackexchange.com/q/426932/6876">source</a>).</p> <p>This means, the solution <code>$(a_0 \dots a_n)^T$</code> of this linear equation gives the polynom <code>$p(x) = \sum_{i=0}^n a_i x^i$</code></p> <p>So the solution exists and is unique <code>$\blacksquare$</code></p> <h2>Straight forward interpolating polynomials</h2> <p>For this algorithm, I’ll find the polynomial in its monomial from <code>$p(x) = \sum_{i=0}^n a_i x^i$</code>. I’ll use the matrix <code>$A$</code> from section “<a href="#Uniqueness">Uniqueness</a>”.</p> <p>You might want to take a look at my article about <a href="../solving-linear-equations-with-gaussian-elimination/" title="Solving linear equations with Gaussian elimination">Gaussian elimination</a>.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">pprintGaus</span><span class="p">(</span><span class="n">A</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Pretty print a n&amp;times;n matrix with a result vector n&amp;times;1. &quot;&quot;&quot;</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">line</span> <span class="o">=</span> <span class="s">&quot;&quot;</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">line</span> <span class="o">+=</span> <span class="nb">str</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">])</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="k">if</span> <span class="n">j</span> <span class="o">==</span> <span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">:</span> <span class="n">line</span> <span class="o">+=</span> <span class="s">&quot;| &quot;</span> <span class="k">print</span><span class="p">(</span><span class="n">line</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;&quot;</span><span class="p">)</span> <span class="k">def</span> <span class="nf">pprintPolynomial</span><span class="p">(</span><span class="n">A</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Pretty print a polynomial. &quot;&quot;&quot;</span> <span class="n">line</span> <span class="o">=</span> <span class="s">&quot;&quot;</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">x</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="k">if</span> <span class="n">i</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">line</span> <span class="o">+=</span> <span class="s">&quot;+&quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="k">else</span><span class="p">:</span> <span class="k">if</span> <span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">line</span> <span class="o">+=</span> <span class="s">&quot;+ x^&quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="k">elif</span> <span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="o">-</span><span class="mi">1</span><span class="p">:</span> <span class="n">line</span> <span class="o">+=</span> <span class="s">&quot;- x^&quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="k">else</span><span class="p">:</span> <span class="n">line</span> <span class="o">+=</span> <span class="s">&quot;+&quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="o">+</span> <span class="s">&quot;&amp;middot;x^&quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="k">print</span><span class="p">(</span><span class="n">line</span><span class="p">)</span> <span class="k">def</span> <span class="nf">gauss</span><span class="p">(</span><span class="n">A</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Solve a linear sysem of equations given by a n&amp;times;n matrix </span> <span class="sd"> with a result vector n&amp;times;1. &quot;&quot;&quot;</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="n">n</span><span class="p">):</span> <span class="c"># Search for maximum in this column</span> <span class="n">maxEl</span> <span class="o">=</span> <span class="nb">abs</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">])</span> <span class="n">maxRow</span> <span class="o">=</span> <span class="n">i</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">])</span> <span class="o">&gt;</span> <span class="n">maxEl</span><span class="p">:</span> <span class="n">maxEl</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="n">maxRow</span> <span class="o">=</span> <span class="n">k</span> <span class="c"># Swap maximum row with current row (column by column)</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">i</span><span class="p">,</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">maxRow</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="n">maxRow</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="n">tmp</span> <span class="c"># Make all rows below this one 0 in current column</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span><span class="n">n</span><span class="p">):</span> <span class="n">c</span> <span class="o">=</span> <span class="o">-</span><span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">]</span><span class="o">/</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">i</span><span class="p">,</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">i</span><span class="o">==</span><span class="n">j</span><span class="p">:</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">else</span><span class="p">:</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">c</span> <span class="o">*</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="c"># Solve equation Ax=b for an upper triangular matrix A</span> <span class="n">x</span><span class="o">=</span><span class="p">[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">n</span><span class="p">]</span><span class="o">/</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">n</span><span class="p">]</span> <span class="o">-=</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="o">*</span> <span class="n">x</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="k">return</span> <span class="n">x</span> <span class="k">def</span> <span class="nf">setGauss</span><span class="p">(</span><span class="n">points</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Create a system of equations for gaussian elimination from </span> <span class="sd"> a set of points. &quot;&quot;&quot;</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">points</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">2</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">x</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">x</span><span class="o">**</span><span class="n">j</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;y&quot;</span><span class="p">]</span> <span class="k">return</span> <span class="n">A</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">from</span> <span class="nn">fractions</span> <span class="kn">import</span> <span class="n">Fraction</span> <span class="c"># Read input data</span> <span class="n">points</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="n">Fraction</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">),</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="n">Fraction</span><span class="p">(</span><span class="mi">1</span><span class="p">)})</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="n">Fraction</span><span class="p">(</span><span class="mi">1</span><span class="p">),</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="n">Fraction</span><span class="p">(</span><span class="mi">1</span><span class="p">)})</span> <span class="n">points</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;x&quot;</span><span class="p">:</span> <span class="n">Fraction</span><span class="p">(</span><span class="mi">2</span><span class="p">),</span> <span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="n">Fraction</span><span class="p">(</span><span class="mi">2</span><span class="p">)})</span> <span class="n">A</span> <span class="o">=</span> <span class="n">setGauss</span><span class="p">(</span><span class="n">points</span><span class="p">)</span> <span class="c"># Print input</span> <span class="n">pprintGaus</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="c"># Calculate solution</span> <span class="n">x</span> <span class="o">=</span> <span class="n">gauss</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="c"># Print result</span> <span class="n">pprintPolynomial</span><span class="p">(</span><span class="n">x</span><span class="p">)</span></code></pre></div> <p>It is also interesting to get the value of <code>$p(x)$</code> at any given point <code>$x \in \mathbb{R}$</code>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">evaluatePolynomial</span><span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="n">x</span><span class="p">):</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">xi</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">i</span><span class="p">,</span> <span class="n">a</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">p</span><span class="p">):</span> <span class="n">y</span> <span class="o">+=</span> <span class="n">a</span> <span class="o">*</span> <span class="n">xi</span> <span class="n">xi</span> <span class="o">*=</span> <span class="n">x</span> <span class="k">return</span> <span class="n">y</span></code></pre></div> <p>Time complexity to get the polynomial: <code>$\frac{1}{3} n^3 + \mathcal{O}(n^2)$</code> (where <code>$n$</code> is the number of points) Space complexity for the polynomial: <code>$\mathcal{O}(n^2)$</code> (where <code>$n$</code> is the number of points)</p> <p>Time complexity to evaluate the value of <code>$p(x)$</code> for any <code>$x \in \mathbb{R}$</code>: <code>$\mathcal{O}(n)$</code>.</p> <h2>Polynomials</h2> <p><code>$\displaystyle \mathbb{R}_n[X] := \left \{p:\mathbb{R} \rightarrow \mathbb{R} | p(x) = \sum_{i=0}^n a_i \cdot x^i \text{ with } a_0, \dots, a_n \in \mathbb{R} \right \}$</code></p> <p>So <code>$\mathbb{R}_n[X]$</code> are all polynomials with real coefficients and degree not higher than latex]n<code>$. $</code>\mathbb{R}_n[X]<code>$ forms a vector space for $</code>n \in \mathbb{N}_0<code>$. The degree of that vector space is $</code>n+1`$.</p> <p>What does that mean?</p> <p>This means you can use different bases for polynomials. The base we usually use for $<code>\mathbb{R}_n[X]</code>$ is $<code>\{x^0, x^1, x^2, x^3, \dots\}</code>$, but you can switch the base.</p> <h2>Lagrange interpolation</h2> <p>Define $<code>n+1</code>$ polynomials like this:</p> <p>$<code>\displaystyle L_{i}(x) := \prod_{j=0 \atop j \neq i}^n \frac{x-x_j}{x_i - x_j}</code>$</p> <p>This means:</p> <p>$<code>\displaystyle L_{i}(x_i) := \prod_{j=0 \atop j \neq i}^n \frac{x_i-x_j}{x_i - x_j} = 1</code>$</p> <p>and</p> <p>$<code>\displaystyle L_{i}(x_p) := \prod_{j=0 \atop j \neq i}^n \frac{x_p-x_j}{x_i - x_j} = 0 \;\; p \in \{0, \dots, n\} \setminus \{i\}</code>$</p> <p>So the polynomial $<code>y_i \cdot L_{i}(x)</code>$ fits the point $<code>(x_i, y_i)</code>$ and is zero for all other points. This implies that</p> <p>$<code>\displaystyle p(x) = \sum_{i=0}^n y_i \cdot L_i(x)</code>$ is an interpolation of our data points. The degree of $<code>p(x)</code>$ is not higher than $<code>n</code>$. You can see that easily when you take a look at the definition of $<code>p(x)</code>$ and $<code>L_i(x)</code>$.</p> <p>The polynomials $<code>L_i(x)</code>$ form another base for $<code>\mathbb{R}_n[X]</code>$.</p> <p>Lagranges way to interpolate polynomials can be implemented like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">lagrangeInterpolation</span><span class="p">(</span><span class="n">points</span><span class="p">):</span> <span class="n">p</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">points</span><span class="p">)):</span> <span class="n">Li</span> <span class="o">=</span> <span class="p">{</span><span class="s">&quot;y&quot;</span><span class="p">:</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;y&quot;</span><span class="p">],</span> <span class="s">&quot;polynomial&quot;</span><span class="p">:[]}</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">points</span><span class="p">)):</span> <span class="k">if</span> <span class="n">j</span> <span class="o">==</span> <span class="n">i</span><span class="p">:</span> <span class="k">continue</span> <span class="n">Li</span><span class="p">[</span><span class="s">&quot;polynomial&quot;</span><span class="p">]</span><span class="o">.</span><span class="n">append</span><span class="p">({</span> <span class="s">&quot;sub&quot;</span><span class="p">:</span> <span class="n">points</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">],</span> <span class="s">&quot;divisor&quot;</span><span class="p">:</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="o">-</span> <span class="n">points</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span> <span class="p">})</span> <span class="n">p</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">Li</span><span class="p">)</span> <span class="k">return</span> <span class="n">p</span> <span class="k">def</span> <span class="nf">evaluateLagrangePolynomial</span><span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="n">x</span><span class="p">):</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">Li</span> <span class="ow">in</span> <span class="n">p</span><span class="p">:</span> <span class="n">prod</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">term</span> <span class="ow">in</span> <span class="n">Li</span><span class="p">[</span><span class="s">&quot;polynomial&quot;</span><span class="p">]:</span> <span class="n">prod</span> <span class="o">*=</span> <span class="p">(</span><span class="n">x</span> <span class="o">-</span> <span class="n">term</span><span class="p">[</span><span class="s">&quot;sub&quot;</span><span class="p">])</span><span class="o">/</span><span class="n">term</span><span class="p">[</span><span class="s">&quot;divisor&quot;</span><span class="p">]</span> <span class="n">y</span> <span class="o">+=</span> <span class="n">Li</span><span class="p">[</span><span class="s">&quot;y&quot;</span><span class="p">]</span><span class="o">*</span><span class="n">prod</span> <span class="k">return</span> <span class="n">y</span></code></pre></div> <p>Time complexity to get the polynomial: $<code>n^2 + \mathcal{O}(n)</code>$ (where $<code>n</code>$ is the number of points) Space complexity for the polynomial: $<code>\mathcal{O}(n^2)</code>$ (where $<code>n</code>$ is the number of points)</p> <p>Time complexity to evaluate the value of $<code>p(x)</code>$ for any $<code>x \in \mathbb{R}</code>$: $<code>\mathcal{O}(n^2)</code>$.</p> <h2>Newton interpolation</h2> <p>Define</p> <p>$<code>\displaystyle N_i(x) := \prod_{j=0}^{i-1} (x-x_j)</code>$</p> <p>So you know that</p> <p>$<code>N_i(x) = 0 \Leftrightarrow \exists p \in \{1, \dots, i\}: x = x_{i-p}</code>$</p> <p>So your polynomial is</p> <p>$<code>\displaystyle p(x) = \sum_{i=0}^n c_i \cdot N_i(x)</code>$</p> <p>for the correct $<code>c_i</code>$. You can do this by solving the following system of equations. Please note that you don’t have to store that matrix to get those $<code>c_i</code>$, <a href="http://en.wikipedia.org/wiki/Divided_differences">divided differences</a> are better.</p> <p>$<code>\begin{pmatrix} 1 &amp; &amp; &amp; &amp; 0 \\ 1 &amp; (x_1 - x_0) &amp; &amp; &amp; \\ 1 &amp; (x_2 - x_0) &amp; (x_2 - x_0)(x_2 - x_1) &amp; &amp; \\ \vdots &amp; \vdots &amp; &amp; \ddots &amp; \\ 1 &amp; (x_n - x_0) &amp; \cdots &amp; &amp; \prod_{i=0}^{n-1}(x_n - x_i) \\ \end{pmatrix} \cdot \begin{pmatrix} c_0 \\ \vdots \\ c_n \end{pmatrix} = \begin{pmatrix} f_0 \\ \vdots \\ f_n \end{pmatrix}</code>$</p> <p>You can get this lower triangular matrix like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">getGaussSystemForNewton</span><span class="p">(</span><span class="n">points</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">points</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">2</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="n">n</span><span class="o">+</span><span class="mi">2</span><span class="p">):</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">j</span><span class="p">,</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">j</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span><span class="o">*</span><span class="p">(</span><span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">]</span><span class="o">-</span><span class="n">points</span><span class="p">[</span><span class="n">j</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;x&quot;</span><span class="p">])</span> <span class="k">if</span> <span class="n">j</span> <span class="o">==</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">:</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">points</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="s">&quot;y&quot;</span><span class="p">]</span> <span class="k">return</span> <span class="n">A</span></code></pre></div> <p>From my previous posts about <a href="../solving-equations-of-upper-triangular-matrices/">solving equations of upper triangular matrices</a> and <a href="../solving-equations-of-unipotent-lower-triangular-matrices/">lower unitriangular matrices</a> you know that the space complexity of this is in $<code>\Theta(n^2)</code>$.</p> <p>According to Wikipedia, you can use <a href="http://en.wikipedia.org/wiki/Horner%27s_method">Horner’s method</a> to evaluate this Polynom in $`\mathcal{O}(n)$. But I really don’t want to implement this today.</p> <h2>Interactive example</h2> <iframe src="../html5/polynom-interpolation.htm" width="98%" height="700px"></iframe> <ul> <li>Click to add points.</li> <li>Ctrl+Click to remove point.</li> <li>You can enter a function that is valid JavaScript in the text field.</li> </ul> Mathematische Strukturen //martin-thoma.com/mathematische-strukturen/ Sun, 16 Jun 2013 18:14:57 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/mathematische-strukturen <p>Es gibt einen ganzen Haufen an mathematischen Strukturen. Dieser Artikel soll jeweils die Definition und bekannte Beispiele sammeln. Weitere Strukturen bzw. Beispiele können gerne in den Kommentaren genannt werden.</p> <h2>Magma</h2> <div class="definition">Sei `$M$` eine Menge und `$*:M \times M \rightarrow M$` eine auf `$M$` abgeschlossene Abbildung. Dann hei&szlig;t `$(M,*)$` ein <strong>Magma</strong>.</div> <div class="definition">Sei `$(M,*)$` ein Magma. `$(M,*)$` hei&szlig;t <strong>kommutativ</strong> `$:\Leftrightarrow \forall a, b \in M: a*b = b*a$`.</div> <p>Ein Synonym zu „kommutativ“ ist „abelsch“.</p> <p>Beispiele:</p> <ul> <li>Jede Halbgruppe ist auch ein Magma.</li> <li>`$(\mathbb{Z}, -)$` ist ein Magma, aber keine Halbgruppe: `$1-(1-1) = 1-0 = 1 \neq -1 = 0-1 = (1-1)-1$`</li> <li>`$(\mathbb{R} \setminus \{0\}, : )$` ist ein Magma, aber keine Halbgruppe: `$1 : (7:7)=1:1=1 \neq \frac{1}{49} = \frac{1}{7} : 7 = (1:7):7$`</li> </ul> <p>Gegenbeispiele:</p> <ul> <li>`$(\mathbb{N}, : )$` ist nicht abgeschlossen, also kein Magma.</li> <li>`$(\mathbb{N}, - )$` ist nicht abgeschlossen, also kein Magma.</li> </ul> <h2>Halbgruppe</h2> <div class="definition">Sei `$(M, *)$` ein Magma. `$(M, *)$` hei&szlig;t <strong>Halbgruppe</strong> `$:\Leftrightarrow (M, *)$` ist assoziativ.</div> <p>Eine Verknüpfung <code>$*$</code> ist genau dann assoziativ auf einer Menge <code>$M$</code>, wenn gilt: <code>$\forall a,b,c \in M: (a*b)*c = a*(b*c)$</code></p> <p>Beispiele:</p> <ul> <li>Jedes Monoid ist auch eine Halbgruppe.</li> <li>`$(\mathbb{N}_{\geq 1}, +)$` ist eine Halbgruppe, aber kein Monoid.</li> </ul> <h2>Monoid</h2> <div class="definition">Sei `$(M, *)$` eine Halbgruppe. `$(M, *)$` hei&szlig;t <strong>Monoid</strong> `$:\Leftrightarrow (M, *)$` hat ein neutrales Element `$e_M$`</div> <p>Ein Element <code>$e_M \in M$</code> heißt genau dann neutral, wenn gilt: <code>$\forall a \in M: e_M * a = a * e_M = a$</code></p> <p>Beispiele:</p> <ul> <li>Jede Gruppe ist auch ein Monoid.</li> <li>`$(\mathbb{N}_{0}, +)$` ist mit 0 als Neutralelement ein Monoid, aber keine Gruppe.</li> <li>`$(\mathbb{N}_{0}, \cdot)$` ist mit 1 als Neutralelement ein Monoid, aber keine Gruppe.</li> <li>`$(\mathbb{Z}, \cdot)$` ist mit 1 als Neutralelement ein Monoid, aber keine Gruppe.</li> </ul> <h2>Gruppe</h2> <div class="definition">Sei `$(M, *)$` ein Monoid. `$(M, *)$` hei&szlig;t <strong>Gruppe</strong> `$:\Leftrightarrow \forall a \in M: \exists a^{-1} \in M: a * a^{-1} = a^{-1} * a = e_M$` </div> <p>Beispiele:</p> <ul> <li>Jeder Ring `$(R, +, \cdot)$` beinhaltet eine Gruppe `$(R, +)$`.</li> <li>`$(\mathbb{Q}, +)$`</li> <li>`$(\mathbb{R}, +)$`</li> <li>`$(\mathbb{Q} \setminus \{0\}, \cdot)$`</li> <li>`$(\mathbb{R} \setminus \{0\}, \cdot)$`</li> </ul> <h2>Ring</h2> <div class="definition">Sei `$R$` eine Menge und `$+:R \times R \rightarrow R$`, `$\cdot:R \times R \rightarrow R$` Verkn&uuml;pfungen darauf. `$(R, +, \cdot)$` hei&szlig;t <strong>Ring</strong> `$:\Leftrightarrow$` <ul> <li>`$(R,+)$` ist eine kommutative Gruppe (das Neutralelement hei&szlig;e 0),</li> <li>`$(R,\cdot)$` ist eine Halbgruppe und</li> <li>die Distributivgesetze sind erf&uuml;llt.</li> </ul> </div> <p>Die Distributivgesetze lauten:</p> <p><code>$\forall a,b,c,d \in R: (a+b) \cdot c = ac + bc$</code></p> <p>und</p> <p><code>$\forall a,b,c,d \in R: a \cdot (c+d) = ac + ad$</code></p> <p>Außerdem:</p> <div class="definition">Sei `$(R,+,\cdot)$` ein Ring. `$(R,+,\cdot)$` hei&szlig;t <strong>Ring mit Eins</strong> `$:\Leftrightarrow (R, \cdot)$` ist Monoid. </div> <div class="definition">Sei `$(R,+,\cdot)$` ein Ring. `$(R,+,\cdot)$` hei&szlig;t <strong>kommutativer Ring</strong> `$:\Leftrightarrow (R, \cdot)$` ist kommutativ. </div> <p>Beispiele:</p> <ul> <li>Jeder K&ouml;rper ist auch ein Ring.</li> <li>`$(\mathbb{Z}, +, \cdot)$` ist ein kommutativer Ring mit Eins, aber kein K&ouml;rper. Es fehlen die Inversen bei der Multiplikation.</li> </ul> <h2>K&ouml;rper</h2> <div class="definition">Sei `$(K, +, \cdot)$` ein kommutativer Ring mit Eins. `$(K, +, \cdot)$` hei&szlig;t <strong>K&ouml;rper</strong> `$:\Leftrightarrow$` <ul> <li>`$(K,+)$` ist kommutativ.</li> <li>`$(K \setminus \{0\}, \cdot)$` ist kommutative Gruppe.</li> </ul> </div> <p>Beispiele:</p> <ul> <li>`$(\mathbb{Q}, +, \cdot)$`</li> <li>`$(\mathbb{R}, +, \cdot)$`</li> <li>`$(\mathbb{C}, +, \cdot)$`</li> <li>`$(\mathbb{Z} / p \mathbb{Z}, +, \cdot)$`, wobei `$p$` eine Primzahl ist</li> </ul> <h2>Modul</h2> <div class="definition">Sei `$(R, +_R, \cdot_R)$` ein Ring und `$(M, +_M)$` eine kommutative Gruppe. Au&szlig;erdem sei `$\cdot_V: R \times M \rightarrow M$` eine Abbildung. `$(M, R, \cdot_V)$` hei&szlig;t <strong>R-Modul</strong> `$:\Leftrightarrow \forall \lambda, \mu \in R \; x,y \in M:$` <ul> <li>`$1_R \cdot x = x$`</li> <li>`$\lambda \cdot (\mu \cdot x) = (\lambda \cdot \mu) \cdot x$`</li> <li>`$(\lambda + \mu) \cdot x = \lambda \cdot x + \mu \cdot x$`</li> <li>`$\lambda \cdot (x+y) = \lambda \cdot x + \lambda \cdot y$`</li> </ul> </div> <p>Beispiele:</p> <ul> <li>Jeder K-Vektorraum ist auch ein K-Modul.</li> <li>Das `$\mathbb{Z}$`-Modul `$\mathbb{Z}/2 \mathbb{Z}$` ist ein Modul ohne Basis, also kein Vektorraum.</li> </ul> <h2>Vektorraum</h2> <div class="definition">Sei `$(K, +_K, \cdot_K)$` ein K&ouml;rper und `$(V,+_V)$` eine kommutative Gruppe. Au&szlig;erdem sei `$\cdot_V: K \times V \rightarrow V$` eine <strong>skalalre Multiplikation</strong>. `$(V, K, \cdot_V)$` hei&szlig;t <strong>`$K$`-Vektorraum</strong> `$:\Leftrightarrow \forall \lambda, \mu \in K \; x,y \in V:$` <ul> <li>`$1_K \cdot x = x$`</li> <li>`$\lambda \cdot (\mu \cdot x) = (\lambda \cdot \mu) \cdot x$`</li> <li>`$(\lambda + \mu) \cdot x = \lambda \cdot x + \mu \cdot x$`</li> <li>`$\lambda \cdot (x+y) = \lambda \cdot x + \lambda \cdot y$`</li> </ul> </div> <p>Beispiele:</p> <ul> <li>`$(\mathbb{R}[X], \mathbb{R}, \cdot_V)$`: Der Vektorraum der polynome mit Koeffizienten aus `$\mathbb{R}$`.</li> </ul> <h2>Weitere</h2> <h3>Ideal</h3> <div class="definition">Ein Ideal in einem Ring `$(R, +, \cdot)$` ist eine Teilmenge `$I \subseteq R$`, die bez&uuml;glich der Addition eine Untergruppe ist und die folgende Eigenschaft hat: `$\forall x \in I, r \in R: xr \in I \text{ und } rx \in I$`</div> <p>Beispiele:</p> <ul> <li>Kerne von Ringhomomorphismen sind immer Ideale. (Und Ideale sind Kerne von Ringhomomorphismen.)</li> </ul> <h3>Algebra</h3> <div class="definition">Es sei `$R$` ein Ring. Eine `$R$`-Algebra ist ein Ring `$A$` zusammen mit einem Ringhomomorphismus `$\sigma: R \rightarrow A$`, sodass gilt: `$\forall r \in R, a \in A: \sigma(r) \cdot a = a \cdot \sigma(r)$`</div> <p>Beispiele:</p> <ul> <li>Jeder Ring ist eine `$\mathbb{Z}$`-Algebra.</li> </ul> <h3>Integrit&auml;tsring</h3> <div class="definition">Es sei `$R$` ein vom Null-Ring verschiedener Ring. `$R$` hei&szlig;t integrit&auml;tsring `$:\Leftrightarrow R$` ist kommuativ und Nullteilerfrei.</div> <p>Beispiele:</p> <ul> <li>Zu dem Ring `$(\mathbb{Z}, +, \cdot)$` ist `$(\mathbb{Q}, +, \cdot)$` ein Quotientenk&ouml;rper.</li> </ul> <h3>Hauptidealring</h3> <div class="definition">Es sei `$R$` ein Integrit&auml;tsring. `$R$` hei&szlig;t Hauptidealring `$:\Leftrightarrow$` Jedes Ideal `$I \subseteq R$` ist ein Hauptideal.</div> <h3>Quotientenk&ouml;rper</h3> <div class="definition">Es sei `$R$` ein Integrit&auml;tsring. Der kleinste K&ouml;rper, in den `$R$` eingebettet werden kann, wird der Quotientenk&ouml;rper des Integrit&auml;tsrings genannt.</div> <p>Beispiele:</p> <ul> <li>Jeder K&ouml;rper ist ein Integrit&auml;tsring.</li> <li>`$(\mathbb{Z}, +, \cdot)$`</li> </ul> <h2>Hilfsbegriffe</h2> <h3>Ideal</h3> <div class="definition">Sei `$(R, +, \cdot)$` ein Ring und `$I \subseteq R$`. `$I$` hei&szlig;t Ideal `$:\Leftrightarrow$` <ol style="list-style-type:lower-roman"> <li>`$(I, +)$` ist eine Gruppe,</li> <li>`$\forall r \in R \forall a \in I: r \cdot a \in I$` und</li> <li>`$\forall r \in R \forall a \in I: a \cdot r \in I$`.</li> </ol></div> <p>Beispiele:</p> <ul> <li>Die Menge `$2\mathbb{Z}$` der geraden ganzen Zahlen ist ein Ideal im Ring`$(\mathbb{Z}, +, \cdot)$`.</li> </ul> <h3>Hauptideal</h3> <div class="definition">Sei `$(R, +, \cdot)$` ein Ring und `$I \subseteq R$` ein Ideal. `$I$` hei&szlig;t Hauptideal `$:\Leftrightarrow I$` wird von einem Element erzeugt.</div> <p>Beispiele:</p> <ul> <li>`$n\mathbb{Z}$`</li> </ul> <h3>Primideal</h3> <div class="definition">Sei `$(R, +, \cdot)$` ein Ring und `$I \subsetneq R$` ein Ideal. `$I$` hei&szlig;t Primideal in `$R :\Leftrightarrow \forall x, y \in R: xy \in I \Rightarrow x \in I \lor y \in I$`</div> <p>Beispiele:</p> <ul> <li>`$2\mathbb{Z}$` ist Primideal in `$(\mathbb{Z}, +, \cdot)$`</li> </ul> <h3>Maximales Ideal</h3> <div class="definition">Sei `$(R, +, \cdot)$` ein Ring und `$I \subsetneq R$` ein Ideal. `$I$` hei&szlig;t maximales Ideal in `$R :\Leftrightarrow$` Es gibt kein Ideal `$J$`, f&uuml;r das gilt: `$I \subsetneq J \subsetneq R$`</div> <p>Beispiele:</p> <ul> <li>In `$(\mathbb{Z},+,\cdot)$` ist jedes Primideal maximal.</li> </ul> Structs in C++ //martin-thoma.com/structs-in-c/ Fri, 07 Jun 2013 16:25:18 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/structs-in-c <p>I guess this article isn’t very interesting, except if you have VERY little experience with C / C++. I only give some complete code examples. If you want some text, you could read <a href="http://en.wikibooks.org/wiki/C%2B%2B_Programming/Structures">C++ Programming/Structures</a> (a wikibook).</p> <h2>Point</h2> <h3>Basic example</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">Point</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">x</span><span class="p">;</span> <span class="kt">double</span> <span class="n">y</span><span class="p">;</span> <span class="p">};</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">Point</span> <span class="n">a</span> <span class="o">=</span> <span class="p">{</span><span class="mi">12</span><span class="p">,</span> <span class="mi">34</span><span class="p">};</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h3>Functions</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#define ABS(a) (a &lt; 0 ? -(a) : a)</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">Point</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">x</span><span class="p">;</span> <span class="kt">double</span> <span class="n">y</span><span class="p">;</span> <span class="p">};</span> <span class="kt">double</span> <span class="nf">getManhattanDistance</span><span class="p">(</span><span class="n">Point</span> <span class="n">a</span><span class="p">,</span> <span class="n">Point</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="o">-</span><span class="n">b</span><span class="p">.</span><span class="n">x</span><span class="p">)</span> <span class="o">+</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="o">-</span><span class="n">b</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">Point</span> <span class="n">a</span> <span class="o">=</span> <span class="p">{</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">};</span> <span class="n">Point</span> <span class="n">b</span> <span class="o">=</span> <span class="p">{</span><span class="mi">3</span><span class="p">,</span> <span class="o">-</span><span class="mi">4</span><span class="p">};</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">b</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">b</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Distance: %.2f</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">getManhattanDistance</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">));</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>More stuff</h2> <h3>Initialization</h3> <p><code>Point a = {}</code> initializes all values of point to 0.</p> <h3>Constructors</h3> <p>You can write constructors for structs:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#define ABS(a) (a &lt; 0 ? -(a) : a)</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">Point</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">x</span><span class="p">;</span> <span class="kt">double</span> <span class="n">y</span><span class="p">;</span> <span class="n">Point</span><span class="p">()</span><span class="o">:</span><span class="n">x</span><span class="p">(</span><span class="mf">2.0</span><span class="p">),</span><span class="n">y</span><span class="p">(</span><span class="mf">5.0</span><span class="p">)</span> <span class="p">{}</span> <span class="n">Point</span><span class="p">(</span><span class="kt">double</span> <span class="n">a</span><span class="p">,</span> <span class="kt">double</span> <span class="n">b</span><span class="p">)</span><span class="o">:</span><span class="n">x</span><span class="p">(</span><span class="mf">9.0</span><span class="p">),</span><span class="n">y</span><span class="p">(</span><span class="mf">9.0</span><span class="p">)</span> <span class="p">{</span><span class="n">x</span><span class="o">=</span><span class="n">a</span><span class="p">;</span> <span class="n">y</span><span class="o">=</span><span class="n">b</span><span class="p">;}</span> <span class="p">};</span> <span class="kt">double</span> <span class="nf">getManhattanDistance</span><span class="p">(</span><span class="n">Point</span> <span class="n">a</span><span class="p">,</span> <span class="n">Point</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="o">-</span><span class="n">b</span><span class="p">.</span><span class="n">x</span><span class="p">)</span> <span class="o">+</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="o">-</span><span class="n">b</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">Point</span> <span class="n">a</span> <span class="o">=</span> <span class="p">{};</span> <span class="n">Point</span> <span class="n">b</span> <span class="o">=</span> <span class="p">{</span><span class="mi">3</span><span class="p">,</span> <span class="o">-</span><span class="mi">4</span><span class="p">};</span> <span class="n">Point</span> <span class="n">c</span><span class="p">;</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">b</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">b</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">c</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">c</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Distance: %.2f</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">getManhattanDistance</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">));</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Which gives:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">./struct-example.out <span class="o">(</span>2.00<span class="p">|</span>5.00<span class="o">)</span> <span class="o">(</span>3.00<span class="p">|</span>-4.00<span class="o">)</span> <span class="o">(</span>2.00<span class="p">|</span>5.00<span class="o">)</span> Distance: 10.00</code></pre></div> <h3>Functions in structs</h3> <p>You can also add functions to structs:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#define ABS(a) (a &lt; 0 ? -(a) : a)</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">Point</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">x</span><span class="p">;</span> <span class="kt">double</span> <span class="n">y</span><span class="p">;</span> <span class="n">Point</span><span class="p">()</span><span class="o">:</span><span class="n">x</span><span class="p">(</span><span class="mf">2.0</span><span class="p">),</span><span class="n">y</span><span class="p">(</span><span class="mf">5.0</span><span class="p">)</span> <span class="p">{}</span> <span class="n">Point</span><span class="p">(</span><span class="kt">double</span> <span class="n">a</span><span class="p">,</span> <span class="kt">double</span> <span class="n">b</span><span class="p">)</span><span class="o">:</span><span class="n">x</span><span class="p">(</span><span class="mf">9.0</span><span class="p">),</span><span class="n">y</span><span class="p">(</span><span class="mf">9.0</span><span class="p">)</span> <span class="p">{</span><span class="n">x</span><span class="o">=</span><span class="n">a</span><span class="p">;</span> <span class="n">y</span><span class="o">=</span><span class="n">b</span><span class="p">;}</span> <span class="kt">double</span> <span class="n">getZeroDist</span><span class="p">()</span> <span class="p">{</span> <span class="k">return</span> <span class="n">ABS</span><span class="p">(</span><span class="n">x</span><span class="p">)</span><span class="o">+</span><span class="n">ABS</span><span class="p">(</span><span class="n">y</span><span class="p">);</span> <span class="p">}</span> <span class="p">};</span> <span class="kt">double</span> <span class="nf">getManhattanDistance</span><span class="p">(</span><span class="n">Point</span> <span class="n">a</span><span class="p">,</span> <span class="n">Point</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="o">-</span><span class="n">b</span><span class="p">.</span><span class="n">x</span><span class="p">)</span> <span class="o">+</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="o">-</span><span class="n">b</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">Point</span> <span class="n">a</span> <span class="o">=</span> <span class="p">{</span><span class="mi">3</span><span class="p">,</span> <span class="o">-</span><span class="mi">10</span><span class="p">};</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;(%.2f|%.2f)</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">x</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">y</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Distance: %.2f</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">a</span><span class="p">.</span><span class="n">getZeroDist</span><span class="p">());</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Result:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">./struct-example.out <span class="o">(</span>3.00<span class="p">|</span>-10.00<span class="o">)</span> Distance: 13.00</code></pre></div> <h2>Read also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Struct_(C_programming_language)">struct (C programming language)</a></li> <li><a href="../cpp-operator-overloading/" title="C++ Operator overloading">Operator overloading</a></li> <li><a href="../a-practical-approach-to-floats/">A practical approach to floats</a>: An example for union</li> <li><a href="../how-do-hash-functions-work/">Connect four</a>: One usage example for structs</li> </ul> <p>Is there anything interesting to say about structs?</p> Calculate square roots //martin-thoma.com/calculate-square-roots/ Thu, 06 Jun 2013 20:54:10 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/calculate-square-roots <p>Suppose you have an equation like this:</p> <p><code>$x^2 = a, \;\;\;\; a \in \mathbb{R}_{\geq 0}$</code></p> <p>Your task is to compute the solution <code>$x \in \mathbb{R}_{\geq 0}$</code>.</p> <p>How do you solve this algorithmically?</p> <h2>Input and output</h2> <p>Write a program that takes two parameters <code>$a, n \in \mathbb{N}_{\geq 1}$</code>:</p> <ul> <li>`$a$`: The number you should take the square root of. `$a$` is not bigger than 65535. To make this a little bit simpler, you can also assume that `$a$` is an integer.</li> <li>`$n$`: Number of iterations you may use</li> </ul> <p>Your program should output exactly one positive floating point number. The decimal separator is a point. At the end of the number should be a newline character <code>\n</code>.</p> <h2>Reference code</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="c1">// Thanks to http://stackoverflow.com/a/15363123/562769</span> <span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#include &lt;gmp.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span> <span class="o">*</span><span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="kt">mpf_t</span> <span class="n">res</span><span class="p">,</span> <span class="n">a</span><span class="p">;</span> <span class="n">mpf_set_default_prec</span><span class="p">(</span><span class="mi">1000000</span><span class="p">);</span> <span class="c1">// Increase this number.</span> <span class="n">mpf_init</span><span class="p">(</span><span class="n">res</span><span class="p">);</span> <span class="n">mpf_init</span><span class="p">(</span><span class="n">a</span><span class="p">);</span> <span class="n">mpf_set_str</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="s">&quot;2&quot;</span><span class="p">,</span> <span class="mi">10</span><span class="p">);</span> <span class="n">mpf_sqrt</span> <span class="p">(</span><span class="n">res</span><span class="p">,</span> <span class="n">a</span><span class="p">);</span> <span class="n">gmp_printf</span><span class="p">(</span><span class="s">&quot;%.1000Ff</span><span class="se">\n\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">res</span><span class="p">);</span> <span class="c1">// Increase this number.</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>You need <a href="http://gmplib.org/manual">GMP</a> (<code>libgmp-dev</code>) to compile this.</p> <p>Compile it like this:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gcc sqrt-reference.c -lgmp -lm -O0 -g3 -o reference.out</code></pre></div> <p>This is the script I use to get the number of correct digits:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">getScore</span><span class="p">(</span><span class="n">program</span><span class="p">,</span> <span class="n">a</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="kn">import</span> <span class="nn">os</span> <span class="n">os</span><span class="o">.</span><span class="n">system</span><span class="p">(</span><span class="s">&quot;./reference.out &quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="o">+</span> <span class="s">&quot; &gt; reference.txt&quot;</span><span class="p">)</span> <span class="n">os</span><span class="o">.</span><span class="n">system</span><span class="p">(</span><span class="s">&quot;./&quot;</span> <span class="o">+</span> <span class="n">program</span> <span class="o">+</span> <span class="s">&quot; &quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="o">+</span> <span class="s">&quot; &quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">+</span> <span class="s">&quot; &gt; result.txt&quot;</span><span class="p">)</span> <span class="n">f</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="s">&#39;reference.txt&#39;</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span> <span class="n">reference</span> <span class="o">=</span> <span class="n">f</span><span class="o">.</span><span class="n">read</span><span class="p">()</span> <span class="n">f</span><span class="o">.</span><span class="n">close</span><span class="p">()</span> <span class="n">f</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="s">&#39;result.txt&#39;</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span> <span class="n">result</span> <span class="o">=</span> <span class="n">f</span><span class="o">.</span><span class="n">read</span><span class="p">()</span> <span class="n">f</span><span class="o">.</span><span class="n">close</span><span class="p">()</span> <span class="n">points</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">areEqual</span> <span class="o">=</span> <span class="bp">True</span> <span class="k">while</span> <span class="n">reference</span><span class="p">[</span><span class="n">points</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span> <span class="ow">and</span> <span class="n">result</span><span class="p">[</span><span class="n">points</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">:</span> <span class="k">if</span> <span class="n">reference</span><span class="p">[</span><span class="n">points</span><span class="p">]</span> <span class="o">==</span> <span class="n">result</span><span class="p">[</span><span class="n">points</span><span class="p">]:</span> <span class="n">points</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="k">break</span> <span class="k">if</span> <span class="n">points</span> <span class="o">&gt;=</span> <span class="mi">2</span><span class="p">:</span> <span class="n">points</span> <span class="o">-=</span> <span class="mi">1</span> <span class="c"># decimal point</span> <span class="k">return</span> <span class="n">points</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">from</span> <span class="nn">argparse</span> <span class="kn">import</span> <span class="n">ArgumentParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">ArgumentParser</span><span class="p">()</span> <span class="c"># Add more options if you like</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-p&quot;</span><span class="p">,</span> <span class="s">&quot;--program&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;program&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;your program&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">,</span> <span class="n">required</span><span class="o">=</span><span class="bp">True</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-a&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&#39;A&#39;</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span> <span class="n">required</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;calculate squre root of a&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-n&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&#39;N&#39;</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span> <span class="n">required</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;maximum n iterations&quot;</span><span class="p">)</span> <span class="n">args</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Points for a=</span><span class="si">%i</span><span class="s"> and n=</span><span class="si">%i</span><span class="s">: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">a</span><span class="p">,</span> <span class="n">args</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="n">getScore</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">program</span><span class="p">,</span> <span class="n">args</span><span class="o">.</span><span class="n">a</span><span class="p">,</span> <span class="n">args</span><span class="o">.</span><span class="n">n</span><span class="p">)))</span></code></pre></div> <h2>Newton's method</h2> <p>How should be choose the initial value? I thought <code>$\frac{a}{2}$</code> could be ok. In a good implementation you’ll probably do this with a lookup table.</p> <p>With long double:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;cmath&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">long</span> <span class="kt">double</span> <span class="nf">newton</span><span class="p">(</span><span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">x</span> <span class="o">=</span> <span class="p">((</span><span class="kt">long</span> <span class="kt">double</span><span class="p">)</span><span class="n">a</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">x</span> <span class="o">=</span> <span class="n">x</span> <span class="o">-</span> <span class="p">(</span><span class="n">x</span><span class="o">*</span><span class="n">x</span> <span class="o">-</span> <span class="n">a</span><span class="p">)</span><span class="o">/</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">x</span><span class="p">);</span> <span class="p">}</span> <span class="k">return</span> <span class="n">x</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span> <span class="o">*</span><span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">!=</span> <span class="mi">3</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Please enter exactly two arguments.&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">a</span> <span class="o">=</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">2</span><span class="p">]);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;%.80Lf</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">newton</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">n</span><span class="p">));</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>I failed to convert this to a version that uses GMP :-/</p> <p>But it converges quite fast:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/06/newton-correct-digits.png"><img src="../images/2013/06/newton-correct-digits.png" alt="Newtons method for calculating square roots" width="" height="" class="size-full wp-image-69511" /></a><p class="wp-caption-text">Newtons method for calculating square roots</p></div> <h2>Exponential identity</h2> <p>According to Wikipedia (Source: <a href="http://en.wikipedia.org/wiki/Methods_of_computing_square_roots#Exponential_identity">Methods of computing square roots</a>) many calculators use the following identity:</p> <p><code>$\displaystyle \sqrt{a} = e^{\frac{1}{2}\ln a}$</code></p> <p>But to calculate this, you need to be able to calculate <code>$e^x$</code> for <code>$x \in \mathbb{R}_{\geq 0}$</code> and <code>$\ln(a)$</code> for <code>$a \in \mathbb{R}_{\geq 0}$</code>.</p> <p>I’ve used the definition of <code>$e^x$</code> to calculate <code>$e^x$</code>: <code>$\displaystyle e^x := \sum_{i = 0}^\infty \frac{x^i}{i!}$</code></p> <p>and:</p> <p><code>$\displaystyle \ln(1+x) =- \sum_{k=0}^\infty \frac{(-x)^{k+1}}{k+1}$</code></p> <p>So I gave it a try:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;cmath&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">long</span> <span class="kt">double</span> <span class="nf">ln</span><span class="p">(</span><span class="kt">int</span> <span class="n">S</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">S</span> <span class="o">-</span> <span class="mi">1</span><span class="p">;</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">result</span> <span class="o">=</span> <span class="n">tmp</span><span class="p">;</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">sign</span> <span class="o">=</span> <span class="mf">1.0</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">2</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="o">/</span><span class="mi">2</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">tmp</span> <span class="o">*=</span> <span class="p">(</span><span class="n">S</span><span class="o">-</span><span class="mi">1</span><span class="p">);</span> <span class="n">sign</span> <span class="o">*=</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="n">result</span> <span class="o">+=</span> <span class="n">sign</span><span class="o">*</span><span class="n">tmp</span><span class="o">/</span><span class="n">i</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">result</span><span class="p">;</span> <span class="p">}</span> <span class="kt">long</span> <span class="kt">double</span> <span class="nf">e</span><span class="p">(</span><span class="kt">long</span> <span class="kt">double</span> <span class="n">x</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">numerator</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">denominator</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="kt">long</span> <span class="kt">double</span> <span class="n">result</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">1</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="o">/</span><span class="mi">2</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">numerator</span> <span class="o">*=</span> <span class="n">x</span><span class="p">;</span> <span class="n">denominator</span> <span class="o">*=</span> <span class="n">i</span><span class="p">;</span> <span class="n">result</span> <span class="o">+=</span> <span class="n">numerator</span><span class="o">/</span><span class="n">denominator</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">result</span><span class="p">;</span> <span class="p">}</span> <span class="kt">long</span> <span class="kt">double</span> <span class="nf">sqrt</span><span class="p">(</span><span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">e</span><span class="p">(</span><span class="n">ln</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span><span class="o">*</span><span class="mf">0.5</span><span class="p">,</span> <span class="n">n</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span> <span class="o">*</span><span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">!=</span> <span class="mi">3</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Please enter exactly two arguments.&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">a</span> <span class="o">=</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">2</span><span class="p">]);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;%.80Lf</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">sqrt</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">n</span><span class="p">));</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>This converges VERY slow: For <code>$a = 2$</code></p> <ul> <li>`$n=1$`: 1 digit correct</li> <li>`$n=10$`: 1 digit correct</li> <li>`$n=100$`: 2 digits correct</li> <li>`$n=1000$`: 4 digit correct</li> <li>`$n=10,000$`: 5 digit correct</li> <li>`$n=100,000$`: 5 digit correct</li> <li>`$n=1,000,000$`: 6 digit correct</li> </ul> <p>Ok, lets take a better Taylor series for calculating <code>$e^x$</code>: <code>$\displaystyle e^x = \sum_{k=0}^\infty \frac{x^{-1+2 k} (2 \cdot k+x)}{(2\cdot k)!}$</code></p> <p>This didn’t change anything! I’m very surprised … as I’ve calculated <code>$\pi$</code> for another article, changing the series to something similar improved the speed of convergence drastically.</p> <h2>See also</h2> <ul> <li>StackOverflow: <a href="http://stackoverflow.com/a/12304868/562769">How does the computer calculate Square roots?</a></li> <li><a href="http://www.intel.com/content/www/us/en/processors/architectures-software-developer-manuals.html">Intel&reg; 64 and IA-32 Architectures Software Developer&rsquo;s Manual</a>: FSQRT, SQRTPS, SQRTSS</li> <li><a href="https://github.com/MartinThoma/algorithms/tree/master/square-root-calculation">Source code</a> of this article</li> </ul> <p>Feel free to add a program that calculates square roots. When they are interesting, I’ll probably add them to this article.</p> Inverting matrices //martin-thoma.com/inverting-matrices/ Sun, 02 Jun 2013 14:01:57 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/inverting-matrices <p>Suppose you have a matrix <code>$A \in \mathbb{R}^{n \times n}$</code> and you want to invert it. I’ve already explained <a href="../wie-bestimme-ich-das-inverse-einer-matrix/">how to invert a matrix</a> (<a href="http://www.purplemath.com/modules/mtrxinvr.htm">English explanation</a>), but I didn’t provide any code and / or runtime analysis.</p> <h2>C++ Code</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;cmath&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">print</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="p">.</span><span class="n">size</span><span class="p">();</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span><span class="o">&lt;</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">j</span> <span class="o">==</span> <span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;| &quot;</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">calculateInverse</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;&amp;</span> <span class="n">A</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="p">.</span><span class="n">size</span><span class="p">();</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// Search for maximum in this column</span> <span class="kt">double</span> <span class="n">maxEl</span> <span class="o">=</span> <span class="n">abs</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">]);</span> <span class="kt">int</span> <span class="n">maxRow</span> <span class="o">=</span> <span class="n">i</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span><span class="o">=</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">;</span> <span class="n">k</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">abs</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">])</span> <span class="o">&gt;</span> <span class="n">maxEl</span><span class="p">)</span> <span class="p">{</span> <span class="n">maxEl</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">];</span> <span class="n">maxRow</span> <span class="o">=</span> <span class="n">k</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="c1">// Swap maximum row with current row (column by column)</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span><span class="o">=</span><span class="n">i</span><span class="p">;</span> <span class="n">k</span><span class="o">&lt;</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="p">;</span><span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">maxRow</span><span class="p">][</span><span class="n">k</span><span class="p">];</span> <span class="n">A</span><span class="p">[</span><span class="n">maxRow</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">];</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// Make all rows below this one 0 in current column</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span><span class="o">=</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">;</span> <span class="n">k</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">c</span> <span class="o">=</span> <span class="o">-</span><span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">]</span><span class="o">/</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">];</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="n">i</span><span class="p">;</span> <span class="n">j</span><span class="o">&lt;</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">i</span><span class="o">==</span><span class="n">j</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">c</span> <span class="o">*</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="c1">// Solve equation Ax=b for an upper triangular matrix A</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="n">i</span><span class="o">&gt;=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">--</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span><span class="o">=</span><span class="n">n</span><span class="p">;</span> <span class="n">k</span><span class="o">&lt;</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="p">;</span><span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">/=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">];</span> <span class="p">}</span> <span class="c1">// this is not necessary, but the output looks nicer:</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">rowModify</span><span class="o">=</span><span class="n">i</span><span class="o">-</span><span class="mi">1</span><span class="p">;</span><span class="n">rowModify</span><span class="o">&gt;=</span><span class="mi">0</span><span class="p">;</span> <span class="n">rowModify</span><span class="o">--</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">columModify</span><span class="o">=</span><span class="n">n</span><span class="p">;</span><span class="n">columModify</span><span class="o">&lt;</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="p">;</span><span class="n">columModify</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">rowModify</span><span class="p">][</span><span class="n">columModify</span><span class="p">]</span> <span class="o">-=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">columModify</span><span class="p">]</span> <span class="o">*</span> <span class="n">A</span><span class="p">[</span><span class="n">rowModify</span><span class="p">][</span><span class="n">i</span><span class="p">];</span> <span class="p">}</span> <span class="c1">// this is not necessary, but the output looks nicer:</span> <span class="n">A</span><span class="p">[</span><span class="n">rowModify</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">n</span><span class="p">;</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="n">line</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">n</span><span class="p">,</span><span class="mi">0</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">double</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">(</span><span class="n">n</span><span class="p">,</span><span class="n">line</span><span class="p">);</span> <span class="c1">// Read input data</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">n</span><span class="o">+</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// Print input</span> <span class="n">print</span><span class="p">(</span><span class="n">A</span><span class="p">);</span> <span class="c1">// Calculate solution</span> <span class="n">calculateInverse</span><span class="p">(</span><span class="n">A</span><span class="p">);</span> <span class="c1">// Print result</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Result:&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">print</span><span class="p">(</span><span class="n">A</span><span class="p">);</span> <span class="p">}</span></code></pre></div> <p>This code is VERY similar to the code of <a href="../solving-linear-equations-with-gaussian-elimination/" title="Solving linear equations with Gaussian elimination">Gaussian elimination</a>. In fact, I’ve only changed all occurrences of <code>n+1</code> to <code>2*n</code>. I also had to change lines 57-70, as we need to do all operations now on a matrix instead of a vector.</p> <h3>Time complexity</h3> <p>Lines 43-52:</p> <p><code>$\displaystyle Operations = \sum_{i=0}^{n-1} \left (\sum_{k=i+1}^{n-1} (\sum_{j=i}^{2n} 1) \right ) = \frac{5}{6} n^3 - \frac{5}{6} n$</code> (see <a href="http://www.wolframalpha.com/input/?i=sum_%7Bi%3D0%7D%5E%7Bn-1%7D+(sum_%7Bk%3Di%2B1%7D%5E%7Bn-1%7D+(sum_%7Bj%3Di%7D%5E%7B2n%7D+1))">Wolfram|Alpha</a>)</p> <p>Lines 63-70:</p> <table> <tbody> <tr> <td><code>$\displaystyle Operations = \sum_{i=0}^{n-1} \left (\sum_{k=0}^{i-1} (\sum_{j=n}^{2n} 1) \right ) = \frac{1}{2} n^3 - \frac{1}{2} n$</code> (see &lt;a href=”http://www.wolframalpha.com/input/?i=sum_%7Bi%3D0%7D%5E%7Bn-1%7D+%28sum_%7Bk%3D0%7D%5E%7Bi-1%7D+%28sum_%7Bj%3Dn%7D%5E%7B2n%7D+1%29%29”))”&gt;Wolfram</td> <td>Alpha&lt;/a&gt;)</td> </tr> </tbody> </table> <p>So we need about <code>$\frac{4}{3} n^3 + \mathcal{O}(n^2)$</code> operations to invert a matrix with Gauß-Elimination.</p> <h3>Space complexity</h3> <p>My algorithm needs space for the inverse matrix, so it is in <code>$\mathcal{O}(n^2)$</code>.</p> <h2>Inverting an upper triangular matrix</h2> <p>Suppose you have an upper triangular matrix <code>$A \in \mathbb{R^{n \times n}}$</code> that you would like to invert. It could look like this:</p> <p><code>$\begin{pmatrix} 2 &amp; 7 &amp; 1 &amp; 8 &amp; 2\\ 0 &amp; 8 &amp; 1 &amp; 8 &amp; 2\\ 0 &amp; 0 &amp; 8 &amp; 4 &amp; 5\\ 0 &amp; 0 &amp; 0 &amp; 9 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 4 \end{pmatrix}$</code></p> <p>How could we improve the algorithm from above to get speed it up?</p> <p>Well, we don’t need lines 24-53 any more, as those lines bring <code>$A$</code> to an upper triangular form. But we still need lines 63-70. So we can improve the algorithm to a complexity of <code>$\frac{1}{2} n^3 + \mathcal{O}(n^2)$</code>.</p> <h2>See also</h2> <p><a href="http://en.wikipedia.org/wiki/Computational_complexity_of_mathematical_operations#Matrix_algebra">Computational complexity of mathematical operations</a></p> Fractions in C++ //martin-thoma.com/fractions-in-cpp/ Sat, 01 Jun 2013 12:00:34 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/fractions-in-cpp <p>Today, I thought I should try to implement a class in C++ that deals with fractions. This is actually quite easy as I’ll show you.</p> <h2>First some math</h2> <h3>Names</h3> <p>When you have a fraction <code>$\frac{a}{b}$</code> then <code>$a$</code> is called <em>numerator</em> and <code>$b$</code> is called <em>denominator</em>.</p> <h3>Operations</h3> <p>The rules for basic operations are simple:</p> <p>Addition: <code>$\frac{a}{b} + \frac{c}{d} = \frac{a \cdot d + c \cdot b}{b \cdot d}$</code></p> <p>Subtraction: <code>$\frac{a}{b} - \frac{c}{d} = \frac{a \cdot d - c \cdot b}{b \cdot d}$</code></p> <p>Multiplication: <code>$\frac{a}{b} \cdot \frac{c}{d} = \frac{a \cdot c}{b \cdot d}$</code></p> <p>Division: <code>$\frac{a}{b} : \frac{c}{d} = \frac{a \cdot d}{b \cdot c}$</code></p> <h3>Euklids algorithm</h3> <p>You can calculate the greatest common divisor with <a href="http://en.wikipedia.org/wiki/Euclidean_algorithm">Euklids algorithm</a>. If you don’t know it, please read the Wikipedia article.</p> <p>Knowing the greatest common divisor is important, because we want that our Faction class automatically cancels those factors so that the numerator and denominator are as small as possible.</p> <h2>C++ Code</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">class</span> <span class="nc">Fraction</span> <span class="p">{</span> <span class="k">private</span><span class="o">:</span> <span class="c1">// Calculates the greates common divisor with </span> <span class="c1">// Euclid&#39;s algorithm</span> <span class="c1">// both arguments have to be positive</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">gcd</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">a</span><span class="p">,</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">while</span> <span class="p">(</span><span class="n">a</span> <span class="o">!=</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">a</span> <span class="o">&gt;</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="n">a</span> <span class="o">-=</span> <span class="n">b</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">b</span> <span class="o">-=</span> <span class="n">a</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="n">a</span><span class="p">;</span> <span class="p">}</span> <span class="k">public</span><span class="o">:</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">numerator</span><span class="p">,</span> <span class="n">denominator</span><span class="p">;</span> <span class="n">Fraction</span><span class="p">()</span> <span class="p">{</span> <span class="n">numerator</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">denominator</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span><span class="p">,</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">d</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">d</span><span class="o">==</span><span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Denominator may not be 0.&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">exit</span><span class="p">(</span><span class="mi">0</span><span class="p">);</span> <span class="p">}</span> <span class="k">else</span> <span class="k">if</span> <span class="p">(</span><span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">numerator</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">denominator</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">sign</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">n</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">sign</span> <span class="o">*=</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="n">n</span> <span class="o">*=</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="n">d</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">sign</span> <span class="o">*=</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="n">d</span> <span class="o">*=</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">gcd</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">d</span><span class="p">);</span> <span class="n">numerator</span> <span class="o">=</span> <span class="n">n</span><span class="o">/</span><span class="n">tmp</span><span class="o">*</span><span class="n">sign</span><span class="p">;</span> <span class="n">denominator</span> <span class="o">=</span> <span class="n">d</span><span class="o">/</span><span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="k">operator</span> <span class="kt">int</span><span class="p">()</span> <span class="p">{</span><span class="k">return</span> <span class="p">(</span><span class="n">numerator</span><span class="p">)</span><span class="o">/</span><span class="n">denominator</span><span class="p">;}</span> <span class="k">operator</span> <span class="kt">float</span><span class="p">()</span> <span class="p">{</span><span class="k">return</span> <span class="p">((</span><span class="kt">float</span><span class="p">)</span><span class="n">numerator</span><span class="p">)</span><span class="o">/</span><span class="n">denominator</span><span class="p">;}</span> <span class="k">operator</span> <span class="kt">double</span><span class="p">()</span> <span class="p">{</span><span class="k">return</span> <span class="p">((</span><span class="kt">double</span><span class="p">)</span><span class="n">numerator</span><span class="p">)</span><span class="o">/</span><span class="n">denominator</span><span class="p">;}</span> <span class="p">};</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">+</span><span class="p">(</span><span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span> <span class="o">+</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="k">return</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">+=</span><span class="p">(</span><span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span> <span class="o">+</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="n">lhs</span> <span class="o">=</span> <span class="n">tmp</span><span class="p">;</span> <span class="k">return</span> <span class="n">lhs</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">-</span><span class="p">(</span><span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span> <span class="o">-</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="k">return</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">-=</span><span class="p">(</span><span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span> <span class="o">-</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="n">lhs</span> <span class="o">=</span> <span class="n">tmp</span><span class="p">;</span> <span class="k">return</span> <span class="n">lhs</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">*</span><span class="p">(</span><span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="k">return</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">*=</span><span class="p">(</span><span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="n">lhs</span> <span class="o">=</span> <span class="n">tmp</span><span class="p">;</span> <span class="k">return</span> <span class="n">lhs</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">*</span><span class="p">(</span><span class="kt">int</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="p">,</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="k">return</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">*</span><span class="p">(</span><span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">,</span> <span class="kt">int</span> <span class="n">lhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="p">,</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">);</span> <span class="k">return</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="n">Fraction</span> <span class="k">operator</span><span class="o">/</span><span class="p">(</span><span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">lhs</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span><span class="o">&amp;</span> <span class="n">rhs</span><span class="p">)</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">tmp</span><span class="p">(</span><span class="n">lhs</span><span class="p">.</span><span class="n">numerator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">denominator</span><span class="p">,</span> <span class="n">lhs</span><span class="p">.</span><span class="n">denominator</span><span class="o">*</span><span class="n">rhs</span><span class="p">.</span><span class="n">numerator</span><span class="p">);</span> <span class="k">return</span> <span class="n">tmp</span><span class="p">;</span> <span class="p">}</span> <span class="n">std</span><span class="o">::</span><span class="n">ostream</span><span class="o">&amp;</span> <span class="k">operator</span><span class="o">&lt;&lt;</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">ostream</span> <span class="o">&amp;</span><span class="n">strm</span><span class="p">,</span> <span class="k">const</span> <span class="n">Fraction</span> <span class="o">&amp;</span><span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">denominator</span> <span class="o">==</span> <span class="mi">1</span><span class="p">)</span> <span class="p">{</span> <span class="n">strm</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">numerator</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">strm</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">numerator</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;/&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">denominator</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">strm</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">Fraction</span> <span class="n">a</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">3</span><span class="p">);</span> <span class="n">Fraction</span> <span class="nf">b</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span><span class="mi">28</span><span class="p">);</span> <span class="n">Fraction</span> <span class="n">c</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">+</span> <span class="n">b</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be 37/84)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">-</span> <span class="n">b</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be 19/84)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">*</span> <span class="n">b</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be 1/28)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">/</span> <span class="n">b</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be 28/9)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="o">-</span><span class="mi">1</span> <span class="o">*</span> <span class="n">b</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be -3/28)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="n">b</span> <span class="o">*</span> <span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">);</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be -3/28)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">c</span> <span class="o">=</span> <span class="n">Fraction</span><span class="p">(</span><span class="o">-</span><span class="mi">100</span><span class="p">,</span><span class="mi">3</span><span class="p">);</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="kt">int</span><span class="p">)</span><span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be -33)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="kt">float</span><span class="p">)</span><span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be -33.3...)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="kt">double</span><span class="p">)</span><span class="n">c</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be -33.3...)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">a</span> <span class="o">-=</span> <span class="n">b</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">a</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">(should be 19/84)&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>See also</h2> <p>You might also be interested in my article about <a href="../cpp-operator-overloading/" title="C++ Operator overloading">operator overloading</a>.</p> <p>Does anybody know if there is an “official” Fraction class?</p> Solving linear equations with Gaussian elimination //martin-thoma.com/solving-linear-equations-with-gaussian-elimination/ Sun, 26 May 2013 00:01:30 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/solving-linear-equations-with-gaussian-elimination <div class="info">Please note that you should use LU-decomposition to solve linear equations. The following code produces valid solutions, but when your vector \\(b\\) changes you have to do all the work again. LU-decomposition is faster in those cases and not slower in case you don't have to solve equations with the same matrix twice.</div> <p>Suppose you have a system of \(n \in \mathbb{N_{\geq 1}}\) linear equations and variables \(x_1, x_2, \dots, x_n \in \mathbb{R}\):</p> <div>\[ \begin{align} a_{1,1} \cdot x_1 + a_{1,2} x_2 + \dots + a_{1,n} \cdot x_{n} &amp;= b_1\\ a_{2,1} \cdot x_1 + a_{2,2} x_2 + \dots + a_{2,n} \cdot x_{n} &amp;= b_2\\ \vdots &amp;= \vdots\\ a_{n,1} \cdot x_1 + a_{n,2} x_2 + \dots + a_{n,n} \cdot x_{n} &amp;= b_n \end{align}\] </div> <p>All factors \(a_{i,j} \in \mathbb{R}\) for \(i,j \in 1, \dots, n\) can be written in one matrix \(A \in \mathbb{R}^{n \times n}\) and all \(b_i\) can be written as a vector \(b\). You combine all \(x_i\) in the same way to a vector \(x\).</p> <p>So you can write the system of equations as:</p> <p>\(A \cdot x = b\)</p> <h2>How Gaussian elimination works</h2> <p>First, you write \(A\) and (b) in an augmented matrix \((A|b)\):</p> <div>\[ \left(\begin{array}{cccc|c} a_{1,1} &amp; a_{1,2} &amp; \dots &amp; a_{1,n} &amp; b_1\\ a_{2,1} &amp; a_{2,2} &amp; \dots &amp; a_{2,n} &amp; b_2\\ \vdots &amp; \vdots &amp; \ddots &amp; \vdots &amp; \vdots \\ a_{n,1} &amp; a_{n,2} &amp; \dots &amp; a_{n,n} &amp; b_n \end{array}\right)\] </div> <p>On this matrix you may make exactly three operations:</p> <ul> <li>Swap rows</li> <li>Add one row onto another</li> <li>Multiply every factor of one row with a constant</li> </ul> <p>You want to get a triangular matrix. So you subsequently eliminate one variable from the system of equations until you have a matrix like this:</p> <div>\[ \left(\begin{array}{ccccc|c} a_{1,1} &amp; a_{1,2} &amp; a_{1,3} &amp; \dots &amp; a_{1,n} &amp; b_1\\ 0 &amp; a_{2,2} &amp; a_{2,3} &amp; \dots &amp; a_{2,n} &amp; b_2\\ 0 &amp; 0 &amp; a_{3,3} &amp; \dots &amp; a_{3,n} &amp; b_3\\ \vdots &amp; \vdots &amp; \ddots &amp; \ddots&amp; \vdots &amp; \vdots\\ 0 &amp; 0 &amp; \dots &amp; 0 &amp; a_{3,n} &amp; b_n\\ \end{array}\right)\] </div> <p>It’s actually quite simple to get this form:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/05/Gaussian-elimination.png"><img src="../images/2013/05/Gaussian-elimination.png" alt="Pseudocode for Gaussian elimination" width="" height="" class="size-full wp-image-68071" /></a><p class="wp-caption-text">Pseudocode for Gaussian elimination</p></div> <h2>C++ Code</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#579">#include</span> <span style="color:#B44;font-weight:bold">&lt;iostream&gt;</span> <span style="color:#579">#include</span> <span style="color:#B44;font-weight:bold">&lt;cmath&gt;</span> <span style="color:#579">#include</span> <span style="color:#B44;font-weight:bold">&lt;vector&gt;</span> <span style="color:#088;font-weight:bold">using</span> <span style="color:#080;font-weight:bold">namespace</span> std; <span style="color:#088;font-weight:bold">void</span> print(vector&lt; vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; &gt; A) { <span style="color:#0a8;font-weight:bold">int</span> n = A.size(); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> i=<span style="color:#00D">0</span>; i&lt;n; i++) { <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> j=<span style="color:#00D">0</span>; j&lt;n+<span style="color:#00D">1</span>; j++) { cout &lt;&lt; A[i][j] &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#b0b">\t</span><span style="color:#710">&quot;</span></span>; <span style="color:#080;font-weight:bold">if</span> (j == n-<span style="color:#00D">1</span>) { cout &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">| </span><span style="color:#710">&quot;</span></span>; } } cout &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#b0b">\n</span><span style="color:#710">&quot;</span></span>; } cout &lt;&lt; endl; } vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; gauss(vector&lt; vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; &gt; A) { <span style="color:#0a8;font-weight:bold">int</span> n = A.size(); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> i=<span style="color:#00D">0</span>; i&lt;n; i++) { <span style="color:#777">// Search for maximum in this column</span> <span style="color:#0a8;font-weight:bold">double</span> maxEl = abs(A[i][i]); <span style="color:#0a8;font-weight:bold">int</span> maxRow = i; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> k=i+<span style="color:#00D">1</span>; k&lt;n; k++) { <span style="color:#080;font-weight:bold">if</span> (abs(A[k][i]) &gt; maxEl) { maxEl = abs(A[k][i]); maxRow = k; } } <span style="color:#777">// Swap maximum row with current row (column by column)</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> k=i; k&lt;n+<span style="color:#00D">1</span>;k++) { <span style="color:#0a8;font-weight:bold">double</span> tmp = A[maxRow][k]; A[maxRow][k] = A[i][k]; A[i][k] = tmp; } <span style="color:#777">// Make all rows below this one 0 in current column</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> k=i+<span style="color:#00D">1</span>; k&lt;n; k++) { <span style="color:#0a8;font-weight:bold">double</span> c = -A[k][i]/A[i][i]; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> j=i; j&lt;n+<span style="color:#00D">1</span>; j++) { <span style="color:#080;font-weight:bold">if</span> (i==j) { A[k][j] = <span style="color:#00D">0</span>; } <span style="color:#080;font-weight:bold">else</span> { A[k][j] += c * A[i][j]; } } } } <span style="color:#777">// Solve equation Ax=b for an upper triangular matrix A</span> vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; x(n); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> i=n-<span style="color:#00D">1</span>; i&gt;=<span style="color:#00D">0</span>; i--) { x[i] = A[i][n]/A[i][i]; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> k=i-<span style="color:#00D">1</span>;k&gt;=<span style="color:#00D">0</span>; k--) { A[k][n] -= A[k][i] * x[i]; } } <span style="color:#080;font-weight:bold">return</span> x; } <span style="color:#0a8;font-weight:bold">int</span> main() { <span style="color:#0a8;font-weight:bold">int</span> n; cin &gt;&gt; n; vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; line(n+<span style="color:#00D">1</span>,<span style="color:#00D">0</span>); vector&lt; vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; &gt; A(n,line); <span style="color:#777">// Read input data</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> i=<span style="color:#00D">0</span>; i&lt;n; i++) { <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> j=<span style="color:#00D">0</span>; j&lt;n; j++) { cin &gt;&gt; A[i][j]; } } <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> i=<span style="color:#00D">0</span>; i&lt;n; i++) { cin &gt;&gt; A[i][n]; } <span style="color:#777">// Print input</span> print(A); <span style="color:#777">// Calculate solution</span> vector&lt;<span style="color:#0a8;font-weight:bold">double</span>&gt; x(n); x = gauss(A); <span style="color:#777">// Print result</span> cout &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Result:</span><span style="color:#b0b">\t</span><span style="color:#710">&quot;</span></span>; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#0a8;font-weight:bold">int</span> i=<span style="color:#00D">0</span>; i&lt;n; i++) { cout &lt;&lt; x[i] &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>; } cout &lt;&lt; endl; } </pre></div> </div> </div> <p>You can call it like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>./gauss.out &lt; 3x3.in 1 2 3 | 1 4 5 6 | 1 1 0 1 | 1 Result: 0 -1 1 </pre></div> </div> </div> <h2 id="python-code">Python code</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">pprint</span>(A): n = <span style="color:#369;font-weight:bold">len</span>(A) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">0</span>, n): line = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">for</span> j <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">0</span>, n+<span style="color:#00D">1</span>): line += <span style="color:#369;font-weight:bold">str</span>(A[i][j]) + <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#b0b">\t</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">if</span> j == n-<span style="color:#00D">1</span>: line += <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">| </span><span style="color:#710">&quot;</span></span> print(line) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">gauss</span>(A): n = <span style="color:#369;font-weight:bold">len</span>(A) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">0</span>, n): <span style="color:#777"># Search for maximum in this column</span> maxEl = <span style="color:#369;font-weight:bold">abs</span>(A[i][i]) maxRow = i <span style="color:#080;font-weight:bold">for</span> k <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(i+<span style="color:#00D">1</span>, n): <span style="color:#080;font-weight:bold">if</span> <span style="color:#369;font-weight:bold">abs</span>(A[k][i]) &gt; maxEl: maxEl = <span style="color:#369;font-weight:bold">abs</span>(A[k][i]) maxRow = k <span style="color:#777"># Swap maximum row with current row (column by column)</span> <span style="color:#080;font-weight:bold">for</span> k <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(i, n+<span style="color:#00D">1</span>): tmp = A[maxRow][k] A[maxRow][k] = A[i][k] A[i][k] = tmp <span style="color:#777"># Make all rows below this one 0 in current column</span> <span style="color:#080;font-weight:bold">for</span> k <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(i+<span style="color:#00D">1</span>, n): c = -A[k][i]/A[i][i] <span style="color:#080;font-weight:bold">for</span> j <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(i, n+<span style="color:#00D">1</span>): <span style="color:#080;font-weight:bold">if</span> i == j: A[k][j] = <span style="color:#00D">0</span> <span style="color:#080;font-weight:bold">else</span>: A[k][j] += c * A[i][j] <span style="color:#777"># Solve equation Ax=b for an upper triangular matrix A</span> x = [<span style="color:#00D">0</span> <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(n)] <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(n-<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>): x[i] = A[i][n]/A[i][i] <span style="color:#080;font-weight:bold">for</span> k <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(i-<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>): A[k][n] -= A[k][i] * x[i] <span style="color:#080;font-weight:bold">return</span> x <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">fractions</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">Fraction</span> n = <span style="color:#369;font-weight:bold">input</span>() A = [[<span style="color:#00D">0</span> <span style="color:#080;font-weight:bold">for</span> j <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(n+<span style="color:#00D">1</span>)] <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(n)] <span style="color:#777"># Read input data</span> <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">0</span>, n): line = <span style="color:#369;font-weight:bold">map</span>(Fraction, <span style="color:#369;font-weight:bold">raw_input</span>().split(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>)) <span style="color:#080;font-weight:bold">for</span> j, el <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(line): A[i][j] = el <span style="color:#369;font-weight:bold">raw_input</span>() line = <span style="color:#369;font-weight:bold">raw_input</span>().split(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>) lastLine = <span style="color:#369;font-weight:bold">map</span>(Fraction, line) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">0</span>, n): A[i][n] = lastLine[i] <span style="color:#777"># Print input</span> pprint(A) <span style="color:#777"># Calculate solution</span> x = gauss(A) <span style="color:#777"># Print result</span> line = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Result:</span><span style="color:#b0b">\t</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#00D">0</span>, n): line += <span style="color:#369;font-weight:bold">str</span>(x[i]) + <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#b0b">\t</span><span style="color:#710">&quot;</span></span> print(line) </pre></div> </div> </div> <h2 id="javascript-code">JavaScript code</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** Solve a linear system of equations given by a n&amp;times;n matrix with a result vector n&amp;times;1. */</span> <span style="color:#080;font-weight:bold">function</span> <span style="color:#06B;font-weight:bold">gauss</span>(A) { <span style="color:#080;font-weight:bold">var</span> n = A.length; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#080;font-weight:bold">var</span> i=<span style="color:#00D">0</span>; i&lt;n; i++) { <span style="color:#777">// Search for maximum in this column</span> <span style="color:#080;font-weight:bold">var</span> maxEl = Math.abs(A[i][i]); <span style="color:#080;font-weight:bold">var</span> maxRow = i; <span style="color:#080;font-weight:bold">for</span>(<span style="color:#080;font-weight:bold">var</span> k=i+<span style="color:#00D">1</span>; k&lt;n; k++) { <span style="color:#080;font-weight:bold">if</span> (Math.abs(A[k][i]) &gt; maxEl) { maxEl = Math.abs(A[k][i]); maxRow = k; } } <span style="color:#777">// Swap maximum row with current row (column by column)</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#080;font-weight:bold">var</span> k=i; k&lt;n+<span style="color:#00D">1</span>; k++) { <span style="color:#080;font-weight:bold">var</span> tmp = A[maxRow][k]; A[maxRow][k] = A[i][k]; A[i][k] = tmp; } <span style="color:#777">// Make all rows below this one 0 in current column</span> <span style="color:#080;font-weight:bold">for</span> (k=i+<span style="color:#00D">1</span>; k&lt;n; k++) { <span style="color:#080;font-weight:bold">var</span> c = -A[k][i]/A[i][i]; <span style="color:#080;font-weight:bold">for</span>(<span style="color:#080;font-weight:bold">var</span> j=i; j&lt;n+<span style="color:#00D">1</span>; j++) { <span style="color:#080;font-weight:bold">if</span> (i==j) { A[k][j] = <span style="color:#00D">0</span>; } <span style="color:#080;font-weight:bold">else</span> { A[k][j] += c * A[i][j]; } } } } <span style="color:#777">// Solve equation Ax=b for an upper triangular matrix A</span> <span style="color:#080;font-weight:bold">var</span> x= <span style="color:#080;font-weight:bold">new</span> Array(n); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#080;font-weight:bold">var</span> i=n-<span style="color:#00D">1</span>; i&gt;-<span style="color:#00D">1</span>; i--) { x[i] = A[i][n]/A[i][i]; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#080;font-weight:bold">var</span> k=i-<span style="color:#00D">1</span>; k&gt;-<span style="color:#00D">1</span>; k--) { A[k][n] -= A[k][i] * x[i]; } } <span style="color:#080;font-weight:bold">return</span> x; } </pre></div> </div> </div> <h2 id="php">PHP</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#777">/** * Gaussian elimination * @param array $A matrix * @param array $x vector * @return array solution vector */</span> <span style="color:#080;font-weight:bold">function</span> <span style="color:#06B;font-weight:bold">gauss</span>(<span style="color:#950">$A</span>, <span style="color:#950">$x</span>) { <span style="color:#777"># Just make a single matrix</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$i</span>=<span style="color:#00D">0</span>; <span style="color:#950">$i</span> &lt; <span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$A</span>); <span style="color:#950">$i</span>++) { <span style="color:#950">$A</span>[<span style="color:#950">$i</span>][] = <span style="color:#950">$x</span>[<span style="color:#950">$i</span>]; } <span style="color:#950">$n</span> = <span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$A</span>); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$i</span>=<span style="color:#00D">0</span>; <span style="color:#950">$i</span> &lt; <span style="color:#950">$n</span>; <span style="color:#950">$i</span>++) { <span style="color:#777"># Search for maximum in this column</span> <span style="color:#950">$maxEl</span> = <span style="color:#369;font-weight:bold">abs</span>(<span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$i</span>]); <span style="color:#950">$maxRow</span> = <span style="color:#950">$i</span>; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$k</span>=<span style="color:#950">$i</span>+<span style="color:#00D">1</span>; <span style="color:#950">$k</span> &lt; <span style="color:#950">$n</span>; <span style="color:#950">$k</span>++) { <span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">abs</span>(<span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$i</span>]) &gt; <span style="color:#950">$maxEl</span>) { <span style="color:#950">$maxEl</span> = <span style="color:#369;font-weight:bold">abs</span>(<span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$i</span>]); <span style="color:#950">$maxRow</span> = <span style="color:#950">$k</span>; } } <span style="color:#777"># Swap maximum row with current row (column by column)</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$k</span>=<span style="color:#950">$i</span>; <span style="color:#950">$k</span> &lt; <span style="color:#950">$n</span>+<span style="color:#00D">1</span>; <span style="color:#950">$k</span>++) { <span style="color:#950">$tmp</span> = <span style="color:#950">$A</span>[<span style="color:#950">$maxRow</span>][<span style="color:#950">$k</span>]; <span style="color:#950">$A</span>[<span style="color:#950">$maxRow</span>][<span style="color:#950">$k</span>] = <span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$k</span>]; <span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$k</span>] = <span style="color:#950">$tmp</span>; } <span style="color:#777"># Make all rows below this one 0 in current column</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$k</span>=<span style="color:#950">$i</span>+<span style="color:#00D">1</span>; <span style="color:#950">$k</span> &lt; <span style="color:#950">$n</span>; <span style="color:#950">$k</span>++) { <span style="color:#950">$c</span> = -<span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$i</span>]/<span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$i</span>]; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$j</span>=<span style="color:#950">$i</span>; <span style="color:#950">$j</span> &lt; <span style="color:#950">$n</span>+<span style="color:#00D">1</span>; <span style="color:#950">$j</span>++) { <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$i</span>==<span style="color:#950">$j</span>) { <span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$j</span>] = <span style="color:#00D">0</span>; } <span style="color:#080;font-weight:bold">else</span> { <span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$j</span>] += <span style="color:#950">$c</span> * <span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$j</span>]; } } } } <span style="color:#777"># Solve equation Ax=b for an upper triangular matrix $A</span> <span style="color:#950">$x</span> = <span style="color:#369;font-weight:bold">array_fill</span>(<span style="color:#00D">0</span>, <span style="color:#950">$n</span>, <span style="color:#00D">0</span>); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$i</span>=<span style="color:#950">$n</span>-<span style="color:#00D">1</span>; <span style="color:#950">$i</span> &gt; -<span style="color:#00D">1</span>; <span style="color:#950">$i</span>--) { <span style="color:#950">$x</span>[<span style="color:#950">$i</span>] = <span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$n</span>]/<span style="color:#950">$A</span>[<span style="color:#950">$i</span>][<span style="color:#950">$i</span>]; <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$k</span>=<span style="color:#950">$i</span>-<span style="color:#00D">1</span>; <span style="color:#950">$k</span> &gt; -<span style="color:#00D">1</span>; <span style="color:#950">$k</span>--) { <span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$n</span>] -= <span style="color:#950">$A</span>[<span style="color:#950">$k</span>][<span style="color:#950">$i</span>] * <span style="color:#950">$x</span>[<span style="color:#950">$i</span>]; } } <span style="color:#080;font-weight:bold">return</span> <span style="color:#950">$x</span>; } <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>And some tiny tests:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$A</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">7</span>)); <span style="color:#950">$x</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">3</span>); <span style="color:#950">$result</span> = gauss(<span style="color:#950">$A</span>, <span style="color:#950">$x</span>); <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$result</span>); <span style="color:#777">### array (size=1)</span> <span style="color:#777">### 0 =&gt; float 0.42857142857143 = 3 / 7</span> <span style="color:#950">$A</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">7</span>)); <span style="color:#950">$x</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">0</span>); <span style="color:#950">$result</span> = gauss(<span style="color:#950">$A</span>, <span style="color:#950">$x</span>); <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$result</span>); <span style="color:#777">### array (size=1)</span> <span style="color:#777">### 0 =&gt; int 0</span> <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <table> <tbody> <tr> <td>Test equations with two variables (see [Wolfram</td> <td>Alpha](http://www.wolframalpha.com/input/?i=solve+%7B%7B7%2C+1%7D%2C+%7B5%2C+3%7D%7D+*+%7B%7Bx%7D%2C+%7By%7D%7D+%3D+%7B%7B1%7D%2C+%7B3%7D%7D)):</td> </tr> </tbody> </table> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$A</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">7</span>, <span style="color:#00D">1</span>), <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">5</span>, <span style="color:#00D">3</span>)); <span style="color:#950">$x</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">1</span>, <span style="color:#00D">3</span>); <span style="color:#950">$result</span> = gauss(<span style="color:#950">$A</span>, <span style="color:#950">$x</span>); <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$result</span>); <span style="color:#777">### array (size=2)</span> <span style="color:#777">### 0 =&gt; float 0</span> <span style="color:#777">### 1 =&gt; float 1</span> <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <table> <tbody> <tr> <td>Test equations with two variables (see [Wolfram</td> <td>Alpha](http://www.wolframalpha.com/input/?i=solve+%7B%7B7%2C+1%7D%2C+%7B5%2C+3%7D%7D+*+%7B%7Bx%7D%2C+%7By%7D%7D+%3D+%7B%7B1%7D%2C+%7B1%7D%7D)):</td> </tr> </tbody> </table> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$A</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">7</span>, <span style="color:#00D">1</span>), <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">5</span>, <span style="color:#00D">3</span>)); <span style="color:#950">$x</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">1</span>, <span style="color:#00D">1</span>); <span style="color:#950">$result</span> = gauss(<span style="color:#950">$A</span>, <span style="color:#950">$x</span>); <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$result</span>); <span style="color:#777">### array (size=2)</span> <span style="color:#777">### 0 =&gt; float 0.125</span> <span style="color:#777">### 1 =&gt; float 0.125</span> <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <h2 id="complexity">Complexity</h2> <h3 id="time-complexity">Time complexity</h3> <p>Time complexity is in \(\mathcal{O}(n^3)\) (lines 44 - 53):</p> <div>\[\begin{align} Operations &amp;= \sum_{i=0}^{n-1} \sum_{k=i+1}^{n-1} \sum_{j=i}^{n} 1\\ &amp;= \sum_{i=0}^{n-1} \sum_{k=i+1}^{n-1} (n-i+1) \\ &amp;= \left (\sum_{i=0}^{n-1} \sum_{k=i+1}^{n-1} (n+1) \right ) - \left (\sum_{i=0}^{n-1} \sum_{k=i+1}^{n-1} i \right )\\ &amp;= \dots \\ &amp;= \frac{1}{6} \cdot n \cdot (2 n^2+3 n-5)\\ &amp;= \frac{1}{3} \cdot n^3 + \mathcal{O}(n^2) \end{align}\] </div> <h3 id="space-complexity">Space complexity</h3> <p>Space complexity of this implementation is in \(\mathcal{O}(n)\), but you can easily come down to \(\mathcal{O}(1)\) when you use <code>A[n]</code> for storing <code>x</code>.</p> Generating many prime numbers //martin-thoma.com/generating-many-prime-numbers/ Tue, 21 May 2013 22:50:10 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/generating-many-prime-numbers <p>Today, a fellow student claimed that it would take much time to check the first 1,000,000 numbers for primes. I claimed that it would be a matter of seconds to do so for the first 1,000,000,000 numbers.</p> <p>So, lets prove my claim.</p> <h2>Trivial approach</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt; </span><span class="c1">// cin, cout</span> <span class="cp">#include &lt;cmath&gt; </span><span class="c1">// sqrt</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">unsigned</span> <span class="kt">long</span><span class="o">&gt;</span> <span class="n">primeList</span><span class="p">;</span> <span class="kt">bool</span> <span class="nf">isPrime</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">unsigned</span> <span class="kt">long</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">myIt</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">root</span> <span class="o">=</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span><span class="p">)</span> <span class="n">sqrt</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="k">for</span><span class="p">(</span><span class="n">myIt</span><span class="o">=</span><span class="n">primeList</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">myIt</span> <span class="o">!=</span> <span class="n">primeList</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="n">myIt</span><span class="o">++</span><span class="p">){</span> <span class="k">if</span><span class="p">(</span><span class="n">n</span><span class="o">%</span><span class="p">(</span><span class="o">*</span><span class="n">myIt</span><span class="p">)</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="nb">false</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="k">if</span> <span class="p">((</span><span class="o">*</span><span class="n">myIt</span><span class="p">)</span> <span class="o">&gt;</span> <span class="n">root</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="nb">true</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="nb">true</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="n">primeList</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">2</span><span class="p">);</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="mi">2</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">max</span> <span class="o">=</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">i</span><span class="o">=</span><span class="mi">3</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">max</span><span class="p">;</span> <span class="n">i</span><span class="o">+=</span><span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span><span class="p">(</span><span class="n">isPrime</span><span class="p">(</span><span class="n">i</span><span class="p">))</span> <span class="p">{</span> <span class="n">primeList</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="n">i</span><span class="p">);</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Execute it for 100,000,000:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out <span class="m">100000000</span> &gt; primes.txt real 0m57.274s user 0m41.855s sys 0m15.229s</code></pre></div> <p>So 41 seconds for all primes not bigger than 100,000,000.</p> <p>Now, lets test it for 1,000,000,000:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out <span class="m">1000000000</span> &gt; primes.txt real 18m18.205s user 15m56.904s sys 2m12.500s</code></pre></div> <p>16 minutes … not exactly “seconds”. But please keep in mind that I also wrote the result to a txt-file. This txt file is 502.0 MB big. It takes quite a lot of time to write such an amount of data from memory to disk.</p> <h2>Sieve of Eratosthenes</h2> <h3>A first try</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt; </span><span class="c1">// cin, cout</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">sieveOfEratosthenes</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">bool</span><span class="o">&gt;</span> <span class="n">primesEratosthenes</span> <span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">true</span><span class="p">);</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="mi">2</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">i</span><span class="o">=</span><span class="mi">3</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">+=</span><span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="nb">true</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">j</span><span class="o">=</span><span class="mi">2</span><span class="p">;</span> <span class="n">j</span><span class="o">*</span><span class="n">i</span><span class="o">&lt;=</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">j</span><span class="o">*</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="nb">false</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="n">sieveOfEratosthenes</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>This one takes 1 minute 5 seconds:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">make<span class="p">;</span><span class="nb">time</span> ./generate-prime-list.out <span class="m">1000000000</span> &gt; testPrimes.txt g++ -std<span class="o">=</span>c++0x -Wall -pedantic -O3 -D NDEBUG generate-prime-list.cpp -o generate-prime-list.out real 3m20.436s user 1m4.908s sys 2m11.748s</code></pre></div> <p>I’m getting closer to “seconds”. ☺</p> <h3>ofstream, endl, \n and buffers</h3> <p>Writing 502.0 MB takes some time. It’s not getting better when I pipe this through bash. So lets write it directly:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;fstream&gt; </span><span class="c1">// ofstream</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">sieveOfEratosthenes</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="n">ofstream</span> <span class="n">myfile</span><span class="p">;</span> <span class="n">myfile</span><span class="p">.</span><span class="n">open</span> <span class="p">(</span><span class="s">&quot;huge-prime-list.txt&quot;</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">bool</span><span class="o">&gt;</span> <span class="n">primesEratosthenes</span> <span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">true</span><span class="p">);</span> <span class="n">myfile</span> <span class="o">&lt;&lt;</span> <span class="mi">2</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">i</span><span class="o">=</span><span class="mi">3</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">+=</span><span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="nb">true</span><span class="p">)</span> <span class="p">{</span> <span class="n">myfile</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">j</span><span class="o">=</span><span class="mi">2</span><span class="p">;</span> <span class="n">j</span><span class="o">*</span><span class="n">i</span><span class="o">&lt;=</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">j</span><span class="o">*</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="nb">false</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="n">myfile</span><span class="p">.</span><span class="n">close</span><span class="p">();</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="n">sieveOfEratosthenes</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out 1000000000 real 3m21.249s user 1m4.016s sys 2m12.332s</code></pre></div> <p>Ok, no real change :-/</p> <p>Another idea is to replace <code>endl</code> by <code>\n</code> (see <a href="http://stackoverflow.com/a/5192299/562769">explanation</a>)</p> <p>That was a good try. Now it needs only 46 seconds:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out 1000000000 real 0m49.539s user 0m46.619s sys 0m0.920s</code></pre></div> <p>Another reason why this might be slow could be too many system calls. So I could buffer some and write them in blocks. I could also just write blocks of unsigned long numbers instead of a string representation. This might lead to a much smaller file size which in consequence is faster to write:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;stdio.h&gt; </span><span class="c1">// fopen</span> <span class="cp">#include &lt;iostream&gt; </span><span class="c1">// atoi</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">sieveOfEratosthenes</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="kt">FILE</span><span class="o">*</span> <span class="n">pFile</span><span class="p">;</span> <span class="n">pFile</span> <span class="o">=</span> <span class="n">fopen</span><span class="p">(</span><span class="s">&quot;huge-prime-list.txt&quot;</span><span class="p">,</span> <span class="s">&quot;wb&quot;</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">bool</span><span class="o">&gt;</span> <span class="n">primesEratosthenes</span> <span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">true</span><span class="p">);</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">tmp</span> <span class="o">=</span> <span class="mi">2</span><span class="p">;</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">tmp</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span><span class="p">),</span><span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">i</span><span class="o">=</span><span class="mi">3</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">+=</span><span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="nb">true</span><span class="p">)</span> <span class="p">{</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">i</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span><span class="p">),</span><span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="n">j</span><span class="o">=</span><span class="mi">2</span><span class="p">;</span> <span class="n">j</span><span class="o">*</span><span class="n">i</span><span class="o">&lt;=</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">j</span><span class="o">*</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="nb">false</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="n">fclose</span><span class="p">(</span><span class="n">pFile</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="n">sieveOfEratosthenes</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>And execute it:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out 1000000000 real 0m39.700s user 0m38.546s sys 0m0.640s</code></pre></div> <p>38 seconds for all primes from 2 to 1,000,000,000. The file size is now only 203.4 MB.</p> <p>By the way, simply setting this with <code>setbuf(pFile, NULL);</code> to unbuffered resulted in 50 seconds execution time.</p> <p>You can get the list with this snippet:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;fstream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">!=</span> <span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;You have to specify a file name&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="kt">FILE</span><span class="o">*</span> <span class="n">pFile</span><span class="p">;</span> <span class="n">pFile</span> <span class="o">=</span> <span class="n">fopen</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">],</span> <span class="s">&quot;rb&quot;</span><span class="p">);</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">x</span><span class="p">;</span> <span class="kt">size_t</span> <span class="n">read</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="o">!</span><span class="n">feof</span><span class="p">(</span><span class="n">pFile</span><span class="p">))</span> <span class="p">{</span> <span class="n">read</span> <span class="o">=</span> <span class="n">fread</span><span class="p">(</span><span class="o">&amp;</span><span class="n">x</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">),</span> <span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="p">(</span><span class="kt">void</span><span class="p">)</span> <span class="n">read</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">feof</span><span class="p">(</span><span class="n">pFile</span><span class="p">)){</span> <span class="k">break</span><span class="p">;</span> <span class="c1">// otherwise it duplicates the last entry</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">x</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="n">fclose</span><span class="p">(</span><span class="n">pFile</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span></code></pre></div> <h3>Improve sieving</h3> <p>The following change was suggested by <em>Niklas B.</em>. Thanks!</p> <p>Take a look at the inner for loop. This one does the sieving, so it gets executed very often. In this loop, you have to calculate <code>j*i</code> for checking the condition of the loop and again for setting it to false. You can get rid of one of those operations. Additionally, you don’t have to start sieving at <code>2*p</code>, but you can start at <code>p*p</code> as you already sieved out all multiples of the first, second, …, current-1-th prime.</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;stdio.h&gt; </span><span class="c1">// fopen</span> <span class="cp">#include &lt;iostream&gt; </span><span class="c1">// atoi</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">sieveOfEratosthenes</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="kt">FILE</span><span class="o">*</span> <span class="n">pFile</span><span class="p">;</span> <span class="n">pFile</span> <span class="o">=</span> <span class="n">fopen</span><span class="p">(</span><span class="s">&quot;huge-prime-list.bin&quot;</span><span class="p">,</span> <span class="s">&quot;wb&quot;</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">bool</span><span class="o">&gt;</span> <span class="n">primesEratosthenes</span> <span class="p">(</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">true</span><span class="p">);</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">tmp</span> <span class="o">=</span> <span class="mi">2</span><span class="p">;</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">tmp</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">),</span><span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">i</span><span class="o">=</span><span class="mi">3</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">+=</span><span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="p">{</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">i</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">),</span> <span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">j</span><span class="o">=</span><span class="n">i</span><span class="o">*</span><span class="n">i</span><span class="p">;</span> <span class="n">j</span><span class="o">&lt;=</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">+=</span><span class="n">i</span><span class="p">)</span> <span class="p">{</span> <span class="n">primesEratosthenes</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="nb">false</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="n">fclose</span><span class="p">(</span><span class="n">pFile</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">!=</span> <span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;You have to specify n&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="n">sieveOfEratosthenes</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Execute:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out 1000000000 real 0m24.222s user 0m23.485s sys 0m0.436s</code></pre></div> <h3>primesieve</h3> <p><a href="https://code.google.com/p/primesieve/">Primesieve</a> is a free software program and C++ library that generates prime numbers and prime k-tuplets (twin primes, prime triplets, …) <code>$&lt; 2^{64}$</code> using a highly optimized implementation of the sieve of Eratosthenes.</p> <p>According to the GUI, it finds all 50,847,534 primes below 1,000,000,000 in 0.16 seconds. But write them to a file…</p> <h2>Sieve of Atkin</h2> <p>Arthur Oliver Lonsdale Atkin (July 31, 1925 – December 28, 2008) was a British mathematician who invented this sieve. I’ve implemented it according to the <a href="http://en.wikipedia.org/wiki/Sieve_of_Atkin#Pseudocode">pseudocode provided in Wikipedia</a>. A <a href="http://stackoverflow.com/a/12066272/562769">very long explanation of Atkins sieve</a> is on StackOverflow</p> <h3>My first implementation</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;stdio.h&gt; </span><span class="c1">// fopen</span> <span class="cp">#include &lt;iostream&gt; </span><span class="c1">// atoi</span> <span class="cp">#include &lt;vector&gt;</span> <span class="cp">#include &lt;cmath&gt; </span><span class="c1">// sqrt, ceil, </span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">sieveOfAtkin</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">limit</span><span class="p">)</span> <span class="p">{</span> <span class="kt">FILE</span><span class="o">*</span> <span class="n">pFile</span><span class="p">;</span> <span class="n">pFile</span> <span class="o">=</span> <span class="n">fopen</span><span class="p">(</span><span class="s">&quot;huge-prime-list.bin&quot;</span><span class="p">,</span> <span class="s">&quot;wb&quot;</span><span class="p">);</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">root</span> <span class="o">=</span> <span class="n">ceil</span><span class="p">(</span><span class="n">sqrt</span><span class="p">(</span><span class="n">limit</span><span class="p">));</span> <span class="c1">// initialize the sieve</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">bool</span><span class="o">&gt;</span> <span class="n">is_prime</span><span class="p">(</span><span class="n">limit</span><span class="p">,</span> <span class="nb">false</span><span class="p">);</span> <span class="c1">// put in candidate primes: </span> <span class="c1">// integers which have an odd number of</span> <span class="c1">// representations by certain quadratic forms</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="n">x</span> <span class="o">&lt;=</span> <span class="n">root</span><span class="p">;</span> <span class="n">x</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">xSquare</span> <span class="o">=</span> <span class="n">x</span><span class="o">*</span><span class="n">x</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="n">y</span> <span class="o">&lt;=</span> <span class="n">root</span><span class="p">;</span> <span class="n">y</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="mi">4</span><span class="o">*</span><span class="n">xSquare</span><span class="p">)</span><span class="o">+</span><span class="p">(</span><span class="n">y</span><span class="o">*</span><span class="n">y</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">n</span> <span class="o">&lt;=</span> <span class="n">limit</span> <span class="o">&amp;&amp;</span> <span class="p">(</span><span class="n">n</span> <span class="o">%</span> <span class="mi">12</span> <span class="o">==</span> <span class="mi">1</span> <span class="o">||</span> <span class="n">n</span> <span class="o">%</span> <span class="mi">12</span> <span class="o">==</span> <span class="mi">5</span><span class="p">))</span> <span class="p">{</span> <span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">=</span> <span class="o">!</span><span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">];</span> <span class="p">}</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="mi">3</span><span class="o">*</span><span class="n">xSquare</span><span class="p">)</span><span class="o">+</span><span class="p">(</span><span class="n">y</span><span class="o">*</span><span class="n">y</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">n</span> <span class="o">&lt;=</span> <span class="n">limit</span> <span class="o">&amp;&amp;</span> <span class="n">n</span> <span class="o">%</span> <span class="mi">12</span> <span class="o">==</span> <span class="mi">7</span><span class="p">)</span> <span class="p">{</span> <span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">=</span> <span class="o">!</span><span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">];</span> <span class="p">}</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="mi">3</span><span class="o">*</span><span class="n">xSquare</span><span class="p">)</span><span class="o">-</span><span class="p">(</span><span class="n">y</span><span class="o">*</span><span class="n">y</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">x</span> <span class="o">&gt;</span> <span class="n">y</span> <span class="o">&amp;&amp;</span> <span class="n">n</span> <span class="o">&lt;=</span> <span class="n">limit</span> <span class="o">&amp;&amp;</span> <span class="n">n</span> <span class="o">%</span> <span class="mi">12</span> <span class="o">==</span> <span class="mi">11</span><span class="p">)</span> <span class="p">{</span> <span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">=</span> <span class="o">!</span><span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="c1">// eliminate composites by sieving</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="mi">5</span><span class="p">;</span> <span class="n">n</span> <span class="o">&lt;=</span> <span class="n">root</span><span class="p">;</span> <span class="n">n</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">])</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">add</span> <span class="o">=</span> <span class="n">n</span><span class="o">*</span><span class="n">n</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">k</span> <span class="o">=</span> <span class="n">add</span><span class="p">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">limit</span><span class="p">;</span> <span class="n">k</span> <span class="o">+=</span> <span class="n">add</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// n is prime, omit multiples of its square; this is</span> <span class="c1">// sufficient because composites which managed to get</span> <span class="c1">// on the list cannot be square-free</span> <span class="n">is_prime</span><span class="p">[</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="nb">false</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="c1">// Output primes</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">primTmp</span> <span class="o">=</span> <span class="mi">2</span><span class="p">;</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">primTmp</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">),</span> <span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="n">primTmp</span> <span class="o">=</span> <span class="mi">3</span><span class="p">;</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">primTmp</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">),</span> <span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="mi">5</span><span class="p">;</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="n">limit</span><span class="p">;</span> <span class="n">n</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">is_prime</span><span class="p">[</span><span class="n">n</span><span class="p">])</span> <span class="p">{</span> <span class="n">fwrite</span><span class="p">(</span><span class="o">&amp;</span><span class="n">n</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">),</span> <span class="mi">1</span><span class="p">,</span> <span class="n">pFile</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="n">fclose</span><span class="p">(</span><span class="n">pFile</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">!=</span> <span class="mi">2</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;You have to specify n&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span> <span class="o">=</span> <span class="p">(</span><span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="n">sieveOfAtkin</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Atkins sieve has a much worse performance than Sieve of Eratosthenes:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./generate-prime-list.out 1000000000 real 1m6.001s user 1m4.724s sys 0m0.604s</code></pre></div> <h3>Primegen</h3> <p><a href="http://cr.yp.to/primegen.html">Primegen</a> is an implementation by <a href="http://en.wikipedia.org/wiki/Daniel_J._Bernstein">Daniel J. Bernstein</a>. It’s a little bit cluttered with 80 files and 3854 LOC in total.</p> <p>When I have some time, I’ll update this article and create a new version of my sieve with ideas from Primegen.</p> <p>Primegen is fast:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time</span> ./primes &gt; primes.txt real 0m11.677s user 0m10.649s sys 0m0.708s</code></pre></div> <p>About 11 seconds for writing all primes between 2 and 1,000,000,000 to a txt file.</p> <h2>See also</h2> <p>You might want to try the following Project Euler problem sets:</p> <ul> <li>Project Euler <ul> <li><a href="http://projecteuler.net/problem=3">Problem 3</a>: What is the largest prime factor of the number 600851475143 ?</li> <li><a href="http://projecteuler.net/problem=7">Problem 7</a>: What is the 10 001st prime number?</li> <li><a href="http://projecteuler.net/problem=60">Problem 60</a></li> </ul> </li> <li>SPOJ <ul> <li><a href="http://www.spoj.com/problems/PRIME1/">PRIME1</a></li> <li><a href="http://www.spoj.com/problems/PRIME2/">PRIME2</a></li> <li><a href="http://www.spoj.com/problems/KPRIMES2/">KPRIMES2</a></li> </ul> </li> <li><a href="http://sweet.ua.pt/tos/software/prime_sieve.html">Segmented sieve of Eratosthenes</a></li> <li><a href="http://www.troubleshooters.com/codecorn/primenumbers/primenumbers.htm">Fun with prime numbers</a>: This looks almost like my article. It might be interesting, because the author thought about finding primes above `$10^9$` which I didn't.</li> </ul> <h2>Finally</h2> <p>The last script that took 23 seconds for calculating and writing all primes in 2 to 1,000,000,000 seems to be the best one. Do you know anything else that could get improved? Please provide a working example (e.g. as a <a href="https://gist.github.com/">gist</a>)</p> Solving equations of upper triangular matrices //martin-thoma.com/solving-equations-of-upper-triangular-matrices/ Mon, 20 May 2013 10:41:49 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/solving-equations-of-upper-triangular-matrices <p>Suppose you have an equation like \(R \cdot x = b\) with \(R \in \mathbb{R}^{n \times n}\) and \(x,b \in \mathbb{R}^n\). \(b\) and \(R\) are given and you want to solve for \(x\).</p> <h2>Example</h2> <p>With \(n=5\), the problem could look like this:</p> <p>\[\begin{pmatrix} 2 &amp; 7 &amp; 1 &amp; 8 &amp; 2<br /> 0 &amp; 8 &amp; 1 &amp; 8 &amp; 2<br /> 0 &amp; 0 &amp; 8 &amp; 4 &amp; 5<br /> 0 &amp; 0 &amp; 0 &amp; 9 &amp; 0<br /> 0 &amp; 0 &amp; 0 &amp; 0 &amp; 4 \end{pmatrix} \cdot \begin{pmatrix} x_1 \ x_2 \ x_3 \ x_4 \ x_5 \end{pmatrix} = \begin{pmatrix} 3 \ 1 \ 4 \ 1 \ 5 \end{pmatrix}\]</p> <p>This is only a shorthand for:</p> <p>\[\begin{align} 2 \cdot x_1 + 7 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 + 2 \cdot x_5 &amp;= 3<br /> 8 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 + 2 \cdot x_5 &amp;= 1<br /> 8 \cdot x_3 + 4 \cdot x_4 + 5 \cdot x_5 &amp;= 4<br /> 9 \cdot x_4 + 0 \cdot x_5 &amp;= 1<br /> 4 \cdot x_5 &amp;= 5 \end{align} \]</p> <h3>First step: Solve for \\(x_5\\)</h3> <p>First you see that \(x_5 = \frac{5}{4}\). So you divide \(b\) by the current row.</p> <div class="important">Don't divide through 0. When you would have to divide by 0 and b is 0, this system has an infinite amount of solutions. When you would have to divide by 0 and b is not 0, then this system has no solution.</div> <p>Now you replace every occurrence of \(x_5\) in the system of equations above:</p> <p>\[\begin{align} 2 \cdot x_1 + 7 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 + 2 \cdot \frac{5}{4} &amp;= 3<br /> 8 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 + 2 \cdot \frac{5}{4} &amp;= 1<br /> 8 \cdot x_3 + 4 \cdot x_4 + 5 \cdot \frac{5}{4} &amp;= 4<br /> 9 \cdot x_4 + 0 \cdot \frac{5}{4} &amp;= 1<br /> 4 \cdot \frac{5}{4} &amp;= 5 \end{align} \]</p> <p>Now you make the multiplications and remove the first trivial line.</p> <p>\[ \begin{align} 2 \cdot x_1 + 7 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 + \frac{5}{2} &amp;= 3<br /> 8 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 + \frac{5}{2} &amp;= 1<br /> 8 \cdot x_3 + 4 \cdot x_4 + \frac{25}{4} &amp;= 4<br /> 9 \cdot x_4 + 0 &amp;= 1<br /> \end{align} \]</p> <h3>Second step: update</h3> <p>Get the constant factors to the right side of the equations: \[ \begin{align} 2 \cdot x_1 + 7 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 &amp;= \frac{1}{2} <br /> 8 \cdot x_2 + 1 \cdot x_3 + 8 \cdot x_4 &amp;= -\frac{3}{2} <br /> 8 \cdot x_3 + 4 \cdot x_4 &amp;= -\frac{9}{4}<br /> 9 \cdot x_4 &amp;= 1<br /> \end{align} \]</p> <p>You’re now in the same situation as in the first step. Next you will solve for \(x_4\), then for \(x_3, x_2\) and finally for \(x_1\).</p> <p>This is called “back substitution”.</p> <p><a href="http://www.wolframalpha.com/input/?i=%7B%7B2%2C7%2C1%2C8%2C2%7D%2C%7B0%2C8%2C1%2C8%2C2%7D%2C%7B0%2C0%2C8%2C4%2C5%7D%2C%7B0%2C0%2C0%2C9%2C0%7D%2C%7B0%2C0%2C0%2C0%2C4%7D%7D%5E-1*%7B%7B3%7D%2C%7B1%7D%2C%7B4%7D%2C%7B1%7D%2C%7B5%7D%7D">According to Wolfram|Alpha</a>, the solution is:</p> <p>\[x = \frac{1}{4608} \cdot \begin{pmatrix}4017\-1182\-1552\512\5760\end{pmatrix} = \begin{pmatrix}\frac{1339}{1536} \ -\frac{197}{768} \ -\frac{97}{288} \ \frac{1}{9} \ \frac{5}{4}\end{pmatrix}\]</p> <h2>Python straightforward algorithm</h2> <p>I will use <a href="http://docs.python.org/2/library/fractions.html">fractions</a> for operations as I don’t want to lose precision while dividing.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">solveUpperTriangularMatrix</span>(R, b): <span style="color:#777"># Convert R and b to Fraction</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">fractions</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">Fraction</span> fR, fb = [], [] <span style="color:#080;font-weight:bold">for</span> x, line <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(R): fLine = [] <span style="color:#080;font-weight:bold">for</span> y, el <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(line): fLine.append(Fraction(el)) fR.append(fLine) <span style="color:#080;font-weight:bold">for</span> el <span style="color:#080;font-weight:bold">in</span> b: fb.append(Fraction(el)) <span style="color:#777"># The solution will be here</span> x = [Fraction(<span style="color:#00D">0</span>)] * <span style="color:#369;font-weight:bold">len</span>(b) <span style="color:#080;font-weight:bold">for</span> step <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(b)-<span style="color:#00D">1</span>, <span style="color:#00D">0</span>-<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>): <span style="color:#080;font-weight:bold">if</span> fR[step][step] == <span style="color:#00D">0</span>: <span style="color:#080;font-weight:bold">if</span> fb[step] != <span style="color:#00D">0</span>: <span style="color:#080;font-weight:bold">return</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">No solution</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">else</span>: <span style="color:#080;font-weight:bold">return</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Infinity solutions</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">else</span>: x[step] = fb[step] / fR[step][step] <span style="color:#080;font-weight:bold">for</span> row <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(step-<span style="color:#00D">1</span>, <span style="color:#00D">0</span>-<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>): fb[row] -= fR[row][step]*x[step] <span style="color:#080;font-weight:bold">return</span> x <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: R = [[<span style="color:#00D">2</span>, <span style="color:#00D">7</span>, <span style="color:#00D">1</span>, <span style="color:#00D">8</span>, <span style="color:#00D">2</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">8</span>, <span style="color:#00D">1</span>, <span style="color:#00D">8</span>, <span style="color:#00D">2</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">8</span>, <span style="color:#00D">4</span>, <span style="color:#00D">5</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">9</span>, <span style="color:#00D">0</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">4</span>]] b = [<span style="color:#00D">3</span>, <span style="color:#00D">1</span>, <span style="color:#00D">4</span>, <span style="color:#00D">1</span>, <span style="color:#00D">5</span>] x = solveUpperTriangularMatrix(R, b) print(x) <span style="color:#777"># Convert x to float</span> x = <span style="color:#369;font-weight:bold">map</span>(<span style="color:#369;font-weight:bold">float</span>, x) print(x) </pre></div> </div> </div> <h2>A better algorithm</h2> <p>Just like for <a href="../solving-equations-of-unipotent-lower-triangular-matrices/" title="Solving equations of unipotent lower triangular matrices">unipotent lower triangular matrices</a>, we can operate directly on the given input:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">solveUpperTriangularMatrix</span>(R, b): <span style="color:#777"># Convert R and b to Fraction</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">fractions</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">Fraction</span> <span style="color:#080;font-weight:bold">for</span> x, line <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(R): <span style="color:#080;font-weight:bold">for</span> y, el <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(line): R[x][y] = Fraction(el) <span style="color:#080;font-weight:bold">for</span> x, el <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">enumerate</span>(b): b[x] = Fraction(el) <span style="color:#777"># The solution will be here</span> <span style="color:#080;font-weight:bold">for</span> step <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(<span style="color:#369;font-weight:bold">len</span>(b)-<span style="color:#00D">1</span>, <span style="color:#00D">0</span>-<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>): <span style="color:#080;font-weight:bold">if</span> R[step][step] == <span style="color:#00D">0</span>: <span style="color:#080;font-weight:bold">if</span> b[step] != <span style="color:#00D">0</span>: <span style="color:#080;font-weight:bold">return</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">No solution</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">else</span>: <span style="color:#080;font-weight:bold">return</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Infinity solutions</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">else</span>: b[step] = b[step] / R[step][step] <span style="color:#080;font-weight:bold">for</span> row <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">range</span>(step-<span style="color:#00D">1</span>, <span style="color:#00D">0</span>-<span style="color:#00D">1</span>, -<span style="color:#00D">1</span>): b[row] -= R[row][step]*b[step] <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: R = [[<span style="color:#00D">2</span>, <span style="color:#00D">7</span>, <span style="color:#00D">1</span>, <span style="color:#00D">8</span>, <span style="color:#00D">2</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">8</span>, <span style="color:#00D">1</span>, <span style="color:#00D">8</span>, <span style="color:#00D">2</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">8</span>, <span style="color:#00D">4</span>, <span style="color:#00D">5</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">9</span>, <span style="color:#00D">0</span>], [<span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">0</span>, <span style="color:#00D">4</span>]] b = [<span style="color:#00D">3</span>, <span style="color:#00D">1</span>, <span style="color:#00D">4</span>, <span style="color:#00D">1</span>, <span style="color:#00D">5</span>] solveUpperTriangularMatrix(R, b) print(b) </pre></div> </div> </div> <h2>Conversion to Fraction</h2> <p>You could think that the conversion to fraction is not necessary. But if you simply remove line 5 to 16, you will get:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[1, 0, -1, 0, 1] </pre></div> </div> </div> <p>because of integer arithmetic. When you convert the input to float before passing it to <code>solveUpperTriangularMatrix</code>, you will get</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[0.8717447916666666, -0.25651041666666663, -0.3368055555555556, 0.1111111111111111, 1.25] </pre></div> </div> </div> <p>which is almost the same as when we calculated with Fraction and converted to float afterwards:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>[0.8717447916666666, -0.2565104166666667, -0.3368055555555556, 0.1111111111111111, 1.25] </pre></div> </div> </div> <p>So: Using Fractions needs some computing time, but you will get better results.</p> <h2>Time complexity</h2> <p>I’ll analyze the second algorithm.</p> <p>The conversion of our input data is obviously in \(\mathcal{O}(n^2)\). Let’s only analyse the part after the conversion.</p> <p>Assume that there is exactly one solution and that line 15-21 take \(c_1\) operations and line 24 takes \(c_2\) operations.</p> <p>Then we would have a total of</p> <p>\[\begin{align} \text{Operations} &amp;= \sum_{i=1}^n \left ( c_1 + \sum_{j=1}^{i-1} c_2 \right )<br /> &amp;= \sum_{i=1}^n c_1 + \sum_{i=1}^n \sum_{j=1}^{i-1} c_2<br /> &amp;= n \cdot c_1 + c_2 \cdot \left (\sum_{i=1}^n \sum_{j=1}^{i-1} 1 \right )<br /> &amp;= n \cdot c_1 + c_2 \cdot \left (\sum_{i=1}^n (i-1) \right )<br /> &amp;= n \cdot c_1 + c_2 \cdot \left ((\sum_{i=1}^n i) - (\sum_{i=1}^n 1) \right )<br /> &amp;= n \cdot c_1 + c_2 \cdot \left (\frac{n^2+n}{2} - n \right )<br /> &amp;= n \cdot c_1 + (n^2-n) \cdot \frac{c_2}{2}<br /> \end{align}\]</p> <p>So the algorithms time complexity is in \(\Theta(n^2) \subsetneq \mathcal{O}(n^2)\).</p> <h2>Space complexity</h2> <p>Please note that I take advantage of Pythons dynamic typing system. I think it’s difficult to see space complexity in python programs. But when you make the same in C++, you will see that you will need space in \(\mathcal{O}(n)\) when you do the conversion. Without the conversion, you’re in \(\mathcal{O}(1)\).</p> <p>I guess you might want to leave this choice to the user of your functions. When he wants better results, he should give the input as Fraction. When he wants to get results rather faster, he should give the input as float.</p> <h2>Notes</h2> <p>In this algorithm, we don’t need anything below the diagonal.</p> Solving equations of lower unitriangular matrices //martin-thoma.com/solving-equations-of-unipotent-lower-triangular-matrices/ Sun, 19 May 2013 22:15:59 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/solving-equations-of-unipotent-lower-triangular-matrices <p>Suppose you have an equation like <code>$L \cdot x = b$</code> with <code>$L \in \mathbb{R}^{n \times n}$</code> and <code>$x,b \in \mathbb{R}^n$</code>. <code>$b$</code> and <code>$L$</code> are given and you want to solve for <code>$x$</code>.</p> <h2>Example</h2> <p>With <code>$n=5$</code>, the problem could look like this:</p> <p><code>$\begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 0 &amp; 0\\ 2 &amp; 1 &amp; 0 &amp; 0 &amp; 0\\ 7 &amp; 1 &amp; 1 &amp; 0 &amp; 0\\ 8 &amp; 2 &amp; 8 &amp; 1 &amp; 0\\ 1 &amp; 8 &amp; 2 &amp; 8 &amp; 1 \end{pmatrix} \cdot \begin{pmatrix} x_1 \\ x_2 \\ x_3 \\ x_4 \\ x_5 \end{pmatrix} = \begin{pmatrix} 3 \\ 1 \\ 4 \\ 1 \\ 5 \end{pmatrix}$</code></p> <p>This is only a shorthand for: <code>$ \begin{align} &amp;1 \cdot x_1 &amp;= 3 \\ &amp;2 \cdot x_1 + 1 \cdot x_2 &amp;= 1\\ &amp;7 \cdot x_1 + 1 \cdot x_2 + 1 \cdot x_3 &amp;= 4\\ &amp;8 \cdot x_1 + 2 \cdot x_2 + 8 \cdot x_3 + 1 \cdot x_4 &amp;= 1\\ &amp;1 \cdot x_1 + 8 \cdot x_2 + 2 \cdot x_3 + 8 \cdot x_4 + 1 \cdot x_5 &amp;= 5 \end{align} $</code></p> <p>This is easy to solve, isn’t it?</p> <h3>First step: Solve for `$x_1$`</h3> <p>First you see that <code>$x_1 = 3$</code>. Now you replace every occurence of <code>$x_1$</code> in the system of equations above:</p> <p><code>$ \begin{align} &amp;1 \cdot 3 &amp;= 3 \\ &amp;2 \cdot 3 + 1 \cdot x_2 &amp;= 1\\ &amp;7 \cdot 3 + 1 \cdot x_2 + 1 \cdot x_3 &amp;= 4\\ &amp;8 \cdot 3 + 2 \cdot x_2 + 8 \cdot x_3 + 1 \cdot x_4 &amp;= 1\\ &amp;1 \cdot 3 + 8 \cdot x_2 + 2 \cdot x_3 + 8 \cdot x_4 + 1 \cdot x_5 &amp;= 5 \end{align}$</code></p> <p>Now you make the multiplications and remove the first trivial line.</p> <p><code>$ \begin{align} &amp;6 + 1 \cdot x_2 &amp;= 1\\ &amp;21 + 1 \cdot x_2 + 1 \cdot x_3 &amp;= 4\\ &amp;24 + 2 \cdot x_2 + 8 \cdot x_3 + 1 \cdot x_4 &amp;= 1\\ &amp;3 + 8 \cdot x_2 + 2 \cdot x_3 + 8 \cdot x_4 + 1 \cdot x_5 &amp;= 5 \end{align} $</code></p> <h3>Second step: update</h3> <p>Get the constant factors to the right side of the equations: <code>$ \begin{align} &amp;1 \cdot x_2 &amp;= 1-6=-5\\ &amp;1 \cdot x_2 + 1 \cdot x_3 &amp;= 4-21=-17\\ &amp;2 \cdot x_2 + 8 \cdot x_3 + 1 \cdot x_4 &amp;= 1-24=-23\\ &amp;8 \cdot x_2 + 2 \cdot x_3 + 8 \cdot x_4 + 1 \cdot x_5 &amp;= 5-3=2 \end{align} $</code></p> <p>You can now easily see that you’re in the same situation as in the first step! Next you will solve for <code>$x_2$</code>, then for <code>$x_3, x_4$</code> and finally for <code>$x_5$</code>.</p> <p>This is the reason why solving such a system of equations is sometimes called “forward substitution”.</p> <h2>Python straightforward algorithm</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">):</span> <span class="n">x</span> <span class="o">=</span> <span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">*</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="k">for</span> <span class="n">step</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)):</span> <span class="n">x</span><span class="p">[</span><span class="n">step</span><span class="p">]</span> <span class="o">=</span> <span class="n">b</span><span class="p">[</span><span class="n">step</span><span class="p">]</span> <span class="k">for</span> <span class="n">row</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)):</span> <span class="n">b</span><span class="p">[</span><span class="n">row</span><span class="p">]</span> <span class="o">=</span> <span class="n">b</span><span class="p">[</span><span class="n">row</span><span class="p">]</span> <span class="o">-</span> <span class="n">L</span><span class="p">[</span><span class="n">row</span><span class="p">][</span><span class="n">step</span><span class="p">]</span><span class="o">*</span><span class="n">x</span><span class="p">[</span><span class="n">step</span><span class="p">]</span> <span class="k">return</span> <span class="n">x</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">L</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">2</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">7</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">1</span><span class="p">]]</span> <span class="n">b</span> <span class="o">=</span> <span class="p">[</span><span class="mi">3</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">5</span><span class="p">]</span> <span class="k">print</span><span class="p">(</span><span class="n">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">))</span></code></pre></div> <p>Pretty easy, isn’t it? But can we even do better?</p> <h2>Even better algorithm</h2> <p>Yes, we can!</p> <p>Take a look at what’s happening when row = 0 in line 9. We make a step that is not necessary. Also, we can take the space of b to store x!</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">):</span> <span class="k">for</span> <span class="n">step</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)):</span> <span class="k">for</span> <span class="n">row</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">step</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)):</span> <span class="n">b</span><span class="p">[</span><span class="n">row</span><span class="p">]</span> <span class="o">-=</span> <span class="n">L</span><span class="p">[</span><span class="n">row</span><span class="p">][</span><span class="n">step</span><span class="p">]</span><span class="o">*</span><span class="n">b</span><span class="p">[</span><span class="n">step</span><span class="p">]</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">L</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">2</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">7</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">1</span><span class="p">]]</span> <span class="n">b</span> <span class="o">=</span> <span class="p">[</span><span class="mi">3</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">5</span><span class="p">]</span> <span class="n">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">b</span><span class="p">)</span></code></pre></div> <p>Now it looks super clean, doesn’t it ☺</p> <p>Keep in mind that you have to store b if you need the values after you’ve applied this algorithm. This is the reason why there here. This algorithm “returns” its value by manipulating b.</p> <h2>Time complexity</h2> <p>I’ll analyze the second algorithm.</p> <p>Let’s assume that line 7 takes <code>$c$</code> operations and <code>$n$</code> is the size of <code>$L \in \mathbb{R}^{n \times n}$</code>.</p> <p>Then we would have a total of</p> <p><code>$\begin{align} \text{Operations} &amp;= \sum_{i=1}^n \left ( \sum_{j=i+1}^n c \right )\\ &amp;= c \cdot \sum_{i=1}^n \left ( \sum_{j=i+1}^n 1 \right )\\ &amp;= c \cdot \sum_{i=1}^n (n - i)\\ &amp;= c \cdot \left ( \sum_{i=1}^n n - \sum_{i=1}^n i \right )\\ &amp;= c \cdot \left ( n^2 - \frac{n^2+n}{2} \right )\\ &amp;= \frac{c}{2} (n^2 - n) \end{align}$</code></p> <p>So the algorithms time complexity is in <code>$\Theta(n^2) \subsetneq \mathcal{O}(n^2)$</code>.</p> <h2>Space complexity</h2> <p>Well, thats simple: <code>$\mathcal{O}(1)$</code>!</p> <p>I do ignore the size of the input. So <code>$\mathcal{O}(1)$</code> means: For variable sized input data I do need a constant amount of additional space.</p> <h2>More improvements</h2> <p>In the last algorithm I’ve presented you can see that we actually don’t check the values on or above of the diagonal. This means, the following two function calls do give the same b:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">):</span> <span class="k">for</span> <span class="n">step</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)):</span> <span class="k">for</span> <span class="n">row</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">step</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">b</span><span class="p">)):</span> <span class="n">b</span><span class="p">[</span><span class="n">row</span><span class="p">]</span> <span class="o">-=</span> <span class="n">L</span><span class="p">[</span><span class="n">row</span><span class="p">][</span><span class="n">step</span><span class="p">]</span><span class="o">*</span><span class="n">b</span><span class="p">[</span><span class="n">step</span><span class="p">]</span> <span class="k">return</span> <span class="n">L</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">L</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">2</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">7</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">],</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">1</span><span class="p">]]</span> <span class="n">b</span> <span class="o">=</span> <span class="p">[</span><span class="mi">3</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">5</span><span class="p">]</span> <span class="n">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="n">L</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">10</span><span class="p">,</span> <span class="mi">9</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">7</span><span class="p">,</span> <span class="mi">6</span><span class="p">],</span> <span class="p">[</span><span class="mi">2</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">2</span><span class="p">],</span> <span class="p">[</span><span class="mi">7</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">],</span> <span class="p">[</span><span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">],</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">4</span><span class="p">]]</span> <span class="n">b</span> <span class="o">=</span> <span class="p">[</span><span class="mi">3</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">5</span><span class="p">]</span> <span class="n">solveLowerUnitriangularMatrix</span><span class="p">(</span><span class="n">L</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">b</span><span class="p">)</span></code></pre></div> <p>So, theoretically, we could store some other information on and above of the diagonal. We also don’t change L. Keep this in mind, this might be important in later articles.</p> k-nearest-neighbor classification and k-means - an interactive example //martin-thoma.com/k-nearest-neighbor-classification-interactive-example/ Sun, 19 May 2013 15:23:11 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/k-nearest-neighbor-classification-interactive-example <iframe src="../html5/clustering/clustering.htm" width="98%" height="700px"></iframe> <p>When the circle has exactly the same number of blue / green dots in it, it will be green.</p> <p>When you move the mouse over the box, everything will be calculated and drawn again. This leads to flickering with k-means, as k-means includes a random choice of cluster centers.</p> <h2>Changelog</h2> <table> <tr> <th>Version</th> <th>Change</th> </tr> <tr> <td><span class="hint" title="974b52110126bfd7169622c7041506f56beae1cf">2.2</span></td> <td>Cluster centers have the same color as the clustered points; when one cluster has no points (and there are at least as many points as clusters) everything gets recalculated</td> </tr> <tr> <td><span class="hint" title="1c37b0a860a419668e54c3c6c6189148485d3ea5">2.1</span></td> <td>users can now specify an arbitrary number of classes; ctrl-key change of class was removed; added hints to configuration options</td> </tr> <tr> <td><span class="hint" title="4ed5997089...">2.0</span></td> <td>k-means implemented</td> </tr> <tr> <td>1.0</td> <td>k-nearest neighbor implemented</td> </tr> </table> <p>Code is <a href="https://github.com/MartinThoma/algorithms/tree/master/k-nearest-neighbor">on GitHub</a>. You may use it for free, but you should add a link to this article.</p> <h2>See also</h2> <div style="width: 411px" class="wp-caption aligncenter"><a href="../images/2013/05/k-nearest-neighbor-interesting-setting.png"><img src="../images/2013/05/k-nearest-neighbor-interesting-setting.png" alt="One interesting setting for k=2" width="" height="" class="size-full wp-image-66811" /></a><p class="wp-caption-text">One interesting setting for k=2</p></div> <div style="width: 810px" class="wp-caption aligncenter"><a href="../images/2013/05/k-means-good-vs-bad.png"><img src="../images/2013/05/k-means-good-vs-bad.png" alt="k-means: Good vs. Bad" width="" height="" class="size-full wp-image-67701" /></a><p class="wp-caption-text">k-means: Good vs. Bad</p></div> <ul> <li><a href="http://en.wikipedia.org/wiki/Voronoi_diagram">Voronoi diagram</a></li> <li><a href="http://en.wikipedia.org/wiki/K-nearest_neighbors_algorithm">K-nearset neighbor</a></li> <li><a href="http://en.wikipedia.org/wiki/K-means_clustering">k-means clustering</a></li> <li>Udacity: Introduction to A.I: <a href="https://www.youtube.com/watch?v=zaKjh2N8jN4">k-means</a></li> </ul> The Collatz sequence //martin-thoma.com/the-collatz-sequence/ Thu, 16 May 2013 23:58:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/the-collatz-sequence <p>The goal of this post is to show you some tools that allow you to visualize data. And I also want to analyze some basic characteristics of the Collatz sequence.</p> <p>The Collatz sequences <code>$(c^n_i)$</code> of a number <code>$n \in \mathbb{N}_{&gt; 0}$</code> is defined like this:</p> <p><code>$f:\mathbb{N}_{&gt;0} \rightarrow \mathbb{N}_{&gt; 0}\;\;\;\;f(n) := \begin{cases} \frac{n}{2} &amp; \text{if } n \text{ is even}\\ 3 \cdot n + 1 &amp; \text{if } n \text{ is odd} \end{cases}$</code></p> <p>So the sequence <code>$(c^n_{i})$</code> is defined as:</p> <p><code>$c^n_{i} := \begin{cases} n &amp; \text{if } i = 0\\ f(c^n_i) &amp; \text{otherwise} \end{cases}$</code></p> <p>You can define a directed graph <code>$G=(V, E)$</code> like this:</p> <p><code>$V = \mathbb{N}_{&gt;0}, \;\;\; E = \{(n, f(n)) | n \in V\}$</code></p> <p>I will call this the <em>Collatz graph</em>.</p> <h2>Collatz conjecture</h2> <div class="important"> `$\forall_{n \in \mathbb{N}_{&gt;0}} \exists_{i \in \mathbb{N}_{&gt;0}}: c^n_i = 1$` </div> <p>The Collatz conjecture was not (dis)proved by now. This is astonishing, as it was proposed in 1937 and I think it is very easy to understand.</p> <p>We also don’t know if the Collatz graph is connected. When it is not connected, it could be that one sequence <code>$(c^n_i)$</code> goes to infinity or that there is another circle (<code>$4,2,1,4$</code> is a circle in the Collatz graph).</p> <h2>Small `$n$`</h2> <p>When you go through all possible Collatz sequences with <code>$n \in 1, \dots, 15$</code>, this is what you get:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/collatz-graph.png"><img src="../images/2013/05/collatz-graph.png" alt="A graph for all Collatz sequences `$(c^n_i)$` with `$n\leq15$`" width="" height="" class="size-full wp-image-66201" /></a><p class="wp-caption-text">A graph for all Collatz sequences `$(c^n_i)$` with `$n\leq15$`</p></div> <p>This image was created with the following Python script:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="c"># Based on: http://en.wikipedia.org/wiki/File:Collatz-graph-all-30-no27.svg</span> <span class="k">def</span> <span class="nf">f</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">%</span> <span class="mi">2</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="n">n</span> <span class="o">/</span> <span class="mi">2</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="mi">3</span><span class="o">*</span><span class="n">n</span> <span class="o">+</span> <span class="mi">1</span> <span class="k">def</span> <span class="nf">writeDotfile</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="n">limit</span><span class="p">,</span> <span class="n">explored</span><span class="p">):</span> <span class="n">dotfile</span> <span class="o">=</span> <span class="nb">file</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;w&#39;</span><span class="p">)</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;digraph {</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;node[style=filled,color=&quot;.7 .3 1.0&quot;];</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;1</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;node[style=filled,color=&quot;.95 .1 1&quot;];</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="c">#dotfile.write(&#39;size=&quot;15,8&quot;;\n&#39;)</span> <span class="k">for</span> <span class="n">n</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">limit</span><span class="p">):</span> <span class="k">while</span> <span class="n">n</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">explored</span><span class="p">:</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">+</span> <span class="s">&#39; -&gt; &#39;</span><span class="p">)</span> <span class="n">explored</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="n">n</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">+</span> <span class="s">&#39;;</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="n">dotfile</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;}</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="k">def</span> <span class="nf">createPng</span><span class="p">(</span><span class="n">dotfile</span><span class="p">,</span> <span class="n">base</span><span class="p">,</span> <span class="n">program</span><span class="p">):</span> <span class="kn">import</span> <span class="nn">os</span> <span class="n">command</span> <span class="o">=</span> <span class="n">program</span> <span class="o">+</span> <span class="s">&quot; -Tsvg &quot;</span> <span class="o">+</span> <span class="n">dotfile</span> <span class="o">+</span> <span class="s">&quot; -o &quot;</span> <span class="o">+</span> <span class="n">base</span> <span class="o">+</span> <span class="s">&quot;.svg&quot;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Execute command: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">command</span><span class="p">)</span> <span class="n">os</span><span class="o">.</span><span class="n">system</span><span class="p">(</span><span class="n">command</span><span class="p">)</span> <span class="n">command</span> <span class="o">=</span> <span class="s">&quot;inkscape &quot;</span><span class="o">+</span><span class="n">base</span><span class="o">+</span><span class="s">&quot;.svg&quot;</span><span class="o">+</span><span class="s">&quot; -w 512 --export-png=&quot;</span><span class="o">+</span><span class="n">base</span><span class="o">+</span><span class="s">&quot;.png&quot;</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Execute command: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">command</span><span class="p">)</span> <span class="n">os</span><span class="o">.</span><span class="n">system</span><span class="p">(</span><span class="n">command</span><span class="p">)</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">argparse</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">argparse</span><span class="o">.</span><span class="n">ArgumentParser</span><span class="p">(</span> <span class="n">description</span><span class="o">=</span><span class="s">&quot;Graph for small Collatz sequences&quot;</span> <span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-f&quot;</span><span class="p">,</span> <span class="s">&quot;--file&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;collatz-graph.gv&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;write dot-FILE&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-p&quot;</span><span class="p">,</span> <span class="s">&quot;--program&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;program&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;dot, neato, twopi, circo, fdp, sfdp, osage&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;PROGRAM&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;dot&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-n&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;limit&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="mi">20</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;limit&quot;</span><span class="p">)</span> <span class="n">args</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="n">writeDotfile</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">filename</span><span class="p">,</span> <span class="n">args</span><span class="o">.</span><span class="n">limit</span><span class="p">,</span> <span class="nb">set</span><span class="p">([</span><span class="mi">1</span><span class="p">]))</span> <span class="kn">import</span> <span class="nn">os</span> <span class="n">createPng</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">filename</span><span class="p">,</span> <span class="n">os</span><span class="o">.</span><span class="n">path</span><span class="o">.</span><span class="n">splitext</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">filename</span><span class="p">)[</span><span class="mi">0</span><span class="p">],</span> <span class="n">args</span><span class="o">.</span><span class="n">program</span><span class="p">)</span></code></pre></div> <p>called like this:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python small-numbers.py -n <span class="m">15</span> -p fdp</code></pre></div> <h2>`$n=27$`</h2> <p><code>$n=27$</code> is an enourmously long sequence:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/collatz-27.png"><img src="../images/2013/05/collatz-27.png" alt="Collatz sequence `$c^{27}_i$`" width="" height="" class="size-full wp-image-66351" /></a><p class="wp-caption-text">Collatz sequence `$c^{27}_i$`</p></div> <p>It was created with pgfplots:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">\documentclass[varwidth=true, border=2pt]{standalone} \usepackage[margin=2.5cm]{geometry} %layout \usepackage{pgfplots} \begin{document} \begin{tikzpicture} \begin{axis}[ axis x line=middle, axis y line=middle, enlarge y limits=true, scaled y ticks = false, width=15cm, height=8cm, % size of the image grid = major, grid style={dashed, gray!30}, ylabel=`$c^{27}_i$`, xlabel=`$i$`, legend style={at={(0.1,-0.1)}, anchor=north} ] \addplot[sharp plot, mark=x, blue] table [x=steps, y=n, col sep=comma] {../collatz27.csv}; \end{axis} \end{tikzpicture} \end{document}</code></pre></div> <h2>How long are Collatz sequences?</h2> <p>I’ve been interested in the question how long Collatz sequences are. Of course, they will be longer when <code>$n$</code> is bigger. But how does the choice of <code>$n$</code> influence the number of steps it takes until you reach <code>$c^n_i = 1$</code>?</p> <p>I’ve tested all Collatz sequences with <code>$n \leq 10,000,000$</code>. This is the result:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/collatz-sequence-steps.png"><img src="../images/2013/05/collatz-sequence-steps.png" alt="Collatz sequence steps" width="" height="" class="size-full wp-image-66231" /></a><p class="wp-caption-text">Collatz sequence steps</p></div> <p>For every hexagon, you check how many datapoints <code>$(n,steps)$</code> you have there. This leads to the count. As you can see, step numbers from 50-120 are very common, the rest is very uncommon. The number of steps increases very slow.</p> <p>The data was created as a 116.9 MB csv file with this C++ code:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;map&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="cp">#include &lt;climits&gt; </span><span class="c1">// get maximum value of unsigned long long</span> <span class="cp">#include &lt;cstdlib&gt; </span><span class="c1">// exit</span> <span class="cp">#define SURPRESS_OUTPUT true</span> <span class="cp">#define SHOW_DICT_CREATION false</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">element</span> <span class="p">{</span> <span class="cm">/** What is the next collatz number? */</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">next</span><span class="p">;</span> <span class="cm">/** How many steps does it take until you reach 1? */</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">steps</span><span class="p">;</span> <span class="p">};</span> <span class="n">map</span><span class="o">&lt;</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">,</span> <span class="k">struct</span> <span class="n">element</span><span class="o">&gt;</span> <span class="n">collatz</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">CRITICAL_VALUE</span> <span class="o">=</span> <span class="p">(</span><span class="n">ULLONG_MAX</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">/</span> <span class="mi">3</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">maxAddFromOneEntry</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">maxEntry</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">maxStepsToOne</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">saveULong</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="cm">/** n &gt;= 1 */</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="nf">nextCollatz</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">n</span><span class="o">%</span><span class="mi">2</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">n</span><span class="o">/</span><span class="mi">2</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">n</span> <span class="o">&gt;=</span> <span class="n">CRITICAL_VALUE</span><span class="p">)</span> <span class="p">{</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Critical value is: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">CRITICAL_VALUE</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;n is: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">n</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;saveULong is: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">saveULong</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">exit</span><span class="p">(</span><span class="mi">1</span><span class="p">);</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">3</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">insertCollatz</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">i</span><span class="p">){</span> <span class="k">if</span> <span class="p">(</span><span class="n">collatz</span><span class="p">.</span><span class="n">find</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="o">==</span> <span class="n">collatz</span><span class="p">.</span><span class="n">end</span><span class="p">())</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">SHOW_DICT_CREATION</span> <span class="o">&amp;&amp;</span> <span class="o">!</span><span class="n">SURPRESS_OUTPUT</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; is not in collatz:&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// i is not in collatz</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="o">&gt;</span> <span class="n">steps</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">current</span> <span class="o">=</span> <span class="n">i</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">next</span> <span class="o">=</span> <span class="n">nextCollatz</span><span class="p">(</span><span class="n">current</span><span class="p">);</span> <span class="k">while</span><span class="p">(</span><span class="n">collatz</span><span class="p">.</span><span class="n">find</span><span class="p">(</span><span class="n">current</span><span class="p">)</span> <span class="o">==</span> <span class="n">collatz</span><span class="p">.</span><span class="n">end</span><span class="p">())</span> <span class="p">{</span> <span class="n">steps</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="n">current</span><span class="p">);</span> <span class="n">current</span> <span class="o">=</span> <span class="n">next</span><span class="p">;</span> <span class="n">next</span> <span class="o">=</span> <span class="n">nextCollatz</span><span class="p">(</span><span class="n">current</span><span class="p">);</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="n">steps</span><span class="p">.</span><span class="n">size</span><span class="p">()</span> <span class="o">&gt;</span> <span class="n">maxAddFromOneEntry</span><span class="p">)</span> <span class="p">{</span> <span class="n">maxAddFromOneEntry</span> <span class="o">=</span> <span class="n">steps</span><span class="p">.</span><span class="n">size</span><span class="p">();</span> <span class="p">}</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="o">&gt;::</span><span class="n">reverse_iterator</span> <span class="n">it</span><span class="p">;</span> <span class="k">for</span><span class="p">(</span><span class="n">it</span><span class="o">=</span><span class="n">steps</span><span class="p">.</span><span class="n">rbegin</span><span class="p">();</span> <span class="n">it</span> <span class="o">!=</span> <span class="n">steps</span><span class="p">.</span><span class="n">rend</span><span class="p">();</span> <span class="n">it</span><span class="o">++</span><span class="p">){</span> <span class="k">struct</span> <span class="n">element</span> <span class="n">el</span><span class="p">;</span> <span class="n">el</span><span class="p">.</span><span class="n">next</span> <span class="o">=</span> <span class="n">current</span><span class="p">;</span> <span class="n">el</span><span class="p">.</span><span class="n">steps</span> <span class="o">=</span> <span class="n">collatz</span><span class="p">[</span><span class="n">current</span><span class="p">].</span><span class="n">steps</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span> <span class="n">collatz</span><span class="p">[</span><span class="o">*</span><span class="n">it</span><span class="p">]</span> <span class="o">=</span> <span class="n">el</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">el</span><span class="p">.</span><span class="n">steps</span> <span class="o">&gt;</span> <span class="n">maxStepsToOne</span><span class="p">)</span> <span class="p">{</span> <span class="n">maxStepsToOne</span> <span class="o">=</span> <span class="n">el</span><span class="p">.</span><span class="n">steps</span><span class="p">;</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="o">*</span><span class="n">it</span> <span class="o">&gt;</span> <span class="n">maxEntry</span><span class="p">)</span> <span class="p">{</span> <span class="n">maxEntry</span> <span class="o">=</span> <span class="o">*</span><span class="n">it</span><span class="p">;</span> <span class="p">}</span> <span class="n">current</span> <span class="o">=</span> <span class="o">*</span><span class="n">it</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">SHOW_DICT_CREATION</span> <span class="o">&amp;&amp;</span> <span class="o">!</span><span class="n">SURPRESS_OUTPUT</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">inserted &quot;</span> <span class="o">&lt;&lt;</span> <span class="o">*</span><span class="n">it</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;-&gt;&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">el</span><span class="p">.</span><span class="n">next</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="k">if</span> <span class="p">(</span><span class="n">SHOW_DICT_CREATION</span> <span class="o">&amp;&amp;</span> <span class="o">!</span><span class="n">SURPRESS_OUTPUT</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; was already in collatz.&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">printCollatz</span><span class="p">()</span> <span class="p">{</span> <span class="k">for</span><span class="p">(</span><span class="n">map</span><span class="o">&lt;</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">,</span> <span class="k">struct</span> <span class="n">element</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">it</span><span class="o">=</span><span class="n">collatz</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">it</span><span class="o">!=</span><span class="n">collatz</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="o">++</span><span class="n">it</span><span class="p">)</span> <span class="p">{</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">next</span> <span class="o">=</span> <span class="p">(</span><span class="o">*</span><span class="n">it</span><span class="p">).</span><span class="n">first</span><span class="p">;</span> <span class="k">while</span><span class="p">(</span><span class="n">next</span> <span class="o">!=</span> <span class="mi">1</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">next</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;-&gt;&quot;</span><span class="p">;</span> <span class="n">next</span> <span class="o">=</span> <span class="n">collatz</span><span class="p">[</span><span class="n">next</span><span class="p">].</span><span class="n">next</span><span class="p">;</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="mi">1</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">printSteps</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">max</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;n,steps&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">for</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">i</span><span class="o">=</span><span class="mi">1</span><span class="p">;</span><span class="n">i</span><span class="o">&lt;=</span><span class="n">max</span><span class="p">;</span><span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;,&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">collatz</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">steps</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="k">struct</span> <span class="n">element</span> <span class="n">e</span><span class="p">;</span> <span class="n">e</span><span class="p">.</span><span class="n">next</span> <span class="o">=</span> <span class="mi">4</span><span class="p">;</span> <span class="n">e</span><span class="p">.</span><span class="n">steps</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">collatz</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="n">e</span><span class="p">;</span> <span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">maxCollatz</span> <span class="o">=</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span><span class="p">)</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">1</span><span class="p">]);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">long</span> <span class="kt">long</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">2</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="n">maxCollatz</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">insertCollatz</span><span class="p">(</span><span class="n">i</span><span class="p">);</span> <span class="n">saveULong</span> <span class="o">=</span> <span class="n">i</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">i</span> <span class="o">%</span> <span class="mi">1000000</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;maxAddFromOneEntry: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">maxAddFromOneEntry</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;maxStepsToOne: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">maxStepsToOne</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;maxEntry: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">maxEntry</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;entries: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">collatz</span><span class="p">.</span><span class="n">size</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="c1">//printCollatz();</span> <span class="n">printSteps</span><span class="p">(</span><span class="n">maxCollatz</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Then I’ve processed it with R:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">R -f analyze.R</code></pre></div> <p>analyze.R:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">library(ggplot2) memory.limit(4000) mydata = read.csv(&quot;/home/moose/Downloads/algorithms/collatz/steps.csv&quot;) # Prepare data p&lt;-ggplot(mydata, aes ( x=n,y=steps )) p&lt;-p + geom_hex(bins=30) p&lt;-p + opts(panel.background = theme_rect(fill=&#39;white&#39;, colour=&#39;white&#39;)) # This will save the result in a pdf file called Rplots.pdf p</code></pre></div> <p>And finally, I’ve converted it to png:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">inkscape Rplots.pdf -w <span class="m">512</span> --export-png<span class="o">=</span>collatz-sequence-steps.png</code></pre></div> <p>I’ve explained this a bit more detailed on <a href="http://tex.stackexchange.com/a/114577/5645">StackExchange</a>.</p> <h2>Maximum in sequence</h2> <p>In the following plot you can see <code>$n \in 1, \dots, 10,000,000$</code> on the <code>$x$</code>-axis and the maximum <code>$y = \max(\{a^n_i | i \in \mathbb{N}_{&gt; 0}\})$</code>:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/maxInSequence.png"><img src="../images/2013/05/maxInSequence.png" alt="Hexagonal binpacking plot for maximum in sequence" width="" height="" class="size-full wp-image-66391" /></a><p class="wp-caption-text">Hexagonal binpacking plot for maximum in sequence</p></div> <div class="highlight"><pre><code class="language-text" data-lang="text">library(ggplot2) mydata = read.csv(&quot;../collatz-maxNumber.csv&quot;) # Prepare data p&lt;-ggplot(mydata, aes(x=n, y=maximum)) + scale_y_log10() p&lt;-p + geom_hex(bins=50) p&lt;-p + opts(panel.background = theme_rect(fill=&#39;white&#39;, colour=&#39;white&#39;)) # This will save the result in a pdf file called Rplots.pdf p</code></pre></div> <h2>Execution times</h2> <p>Generating all Collatz sequences up to 10,000,000 items took about 50 seconds. But R needed about 10 minutes to generate images from that.</p> <p>Inkscape didn’t like the heavy plot:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07<span class="nv">$ </span>inkscape Rplots.pdf -w <span class="m">512</span> --export-png<span class="o">=</span>maxInSequence.png <span class="o">(</span>inkscape:26733<span class="o">)</span>: GLib-ERROR **: /build/buildd/glib2.0-2.34.1/./glib/gmem.c:165: failed to allocate <span class="m">3440640</span> bytes ^CTrace/breakpoint <span class="nb">trap</span> <span class="o">(</span>core dumped<span class="o">)</span></code></pre></div> <h2>Maximum in sequence and steps</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/collatz-sequence-and-steps-for-n.png"><img src="../images/2013/05/collatz-sequence-and-steps-for-n.png" alt="Maximum value and number of steps for n up to 10,000" width="" height="" class="size-full wp-image-66481" /></a><p class="wp-caption-text">Maximum value and number of steps for n up to 10,000</p></div> <h2>Read more</h2> <ul> <li><a href="https://github.com/MartinThoma/algorithms/tree/master/collatz">All sources</a> of this article are on GitHub</li> <li><a href="http://www.graphviz.org/Documentation/dotguide.pdf">Dot guide</a>, <a href="http://www.graphviz.org/doc/info/shapes.html">Node shapes</a></li> <li><a href="http://wiki.ubuntuusers.de/R">R on UbuntuUsers</a> (German)</li> <li><a href="http://projecteuler.net/problem=14">Project Euler 14</a></li> </ul> Maps in C++ //martin-thoma.com/maps-in-cpp/ Thu, 16 May 2013 08:52:54 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/maps-in-cpp <p>Maps are one of the most useful datastructures in C++ and there is no excuse for not knowing it.</p> <p>Here is a basic example that shows how you can use it:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt; </span><span class="c1">// cout</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;map&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">map</span><span class="o">&lt;</span><span class="n">string</span><span class="p">,</span> <span class="n">string</span><span class="o">&gt;</span> <span class="n">phonebook</span><span class="p">;</span> <span class="c1">// Put some stuff in it</span> <span class="n">phonebook</span><span class="p">[</span><span class="s">&quot;Martin&quot;</span><span class="p">]</span> <span class="o">=</span> <span class="s">&quot;(0123) 45 678&quot;</span><span class="p">;</span> <span class="n">phonebook</span><span class="p">[</span><span class="s">&quot;Alice&quot;</span><span class="p">]</span> <span class="o">=</span> <span class="s">&quot;+(13) 37 0000&quot;</span><span class="p">;</span> <span class="n">phonebook</span><span class="p">[</span><span class="s">&quot;Bob&quot;</span><span class="p">]</span> <span class="o">=</span> <span class="s">&quot;+(13) 37 0000&quot;</span><span class="p">;</span> <span class="n">phonebook</span><span class="p">[</span><span class="s">&quot;Charlie&quot;</span><span class="p">]</span> <span class="o">=</span> <span class="s">&quot;Alice&quot;</span><span class="p">;</span> <span class="c1">// Look stuff up</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;The phone number of Alice is &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">phonebook</span><span class="p">[</span><span class="s">&quot;Alice&quot;</span><span class="p">]</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Number of phone book entries: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">phonebook</span><span class="p">.</span><span class="n">size</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="c1">// Print everything</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Iterate over all phonebook entries: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">for</span><span class="p">(</span><span class="n">map</span><span class="o">&lt;</span><span class="n">string</span><span class="p">,</span><span class="n">string</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">it</span><span class="o">=</span><span class="n">phonebook</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">it</span><span class="o">!=</span><span class="n">phonebook</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="o">++</span><span class="n">it</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="o">*</span><span class="n">it</span><span class="p">).</span><span class="n">first</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;: &quot;</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="o">*</span><span class="n">it</span><span class="p">).</span><span class="n">second</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// Check if entry exists:</span> <span class="n">string</span> <span class="n">person</span> <span class="o">=</span> <span class="s">&quot;Bob&quot;</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Does &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">person</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; have a phone number ?&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">map</span><span class="o">&lt;</span><span class="n">string</span><span class="p">,</span><span class="n">string</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">it</span> <span class="o">=</span> <span class="n">phonebook</span><span class="p">.</span><span class="n">find</span><span class="p">(</span><span class="n">person</span><span class="p">);</span> <span class="k">if</span><span class="p">(</span><span class="n">it</span> <span class="o">!=</span> <span class="n">phonebook</span><span class="p">.</span><span class="n">end</span><span class="p">())</span> <span class="p">{</span> <span class="c1">//element found:</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Yes! His number is: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">it</span><span class="o">-&gt;</span><span class="n">second</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;No.&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span></code></pre></div> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Map_(computer_science)">Map (Computer Science)</a></li> <li>C++ Reference: <a href="http://www.cplusplus.com/reference/map/map/">general information</a> and <a href="http://www.cplusplus.com/reference/map/map/map/">example</a></li> <li>Map is ordered collection (<a href="http://stackoverflow.com/a/4562771/562769">source</a>)</li> </ul> Google Code Jam – Round 1C 2013 //martin-thoma.com/google-code-jam-round-1c-2013/ Sun, 12 May 2013 15:01:15 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-round-1c-2013 <ul> <li>Problem A (<a href="https://code.google.com/codejam/contest/2437488/dashboard#s=p0">Consonants</a>): <ul> <li>Small Set: 4305/4834 users (89%)</li> <li>Large Set: 1551/3778 users (41%)</li> </ul> <li>Problem B (<a href="https://code.google.com/codejam/contest/2437488/dashboard#s=p1">Pogo</a>): <ul> <li>Small Set: 2537/3129 users (81%)</li> <li>Large Set: 121/638 users (19%)</li> </ul> </li> <li>Problem C (<a href="https://code.google.com/codejam/contest/2437488/dashboard#s=p2">The Great Wall</a>): <ul> <li>Small Set: 934/1260 users (74%)</li> <li>Large Set: 74/330 users (22%)</li> </ul> </li> More information is on <a href="http://www.go-hero.net/jam/13/round/3">go-hero.net</a>. <h2>Consonants</h2> A solution from <a href="http://www.go-hero.net/jam/13/name/nip">nip</a>: <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">s</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">vowels</span> <span class="o">=</span> <span class="p">{</span><span class="s">&#39;a&#39;</span><span class="p">,</span> <span class="s">&#39;e&#39;</span><span class="p">,</span> <span class="s">&#39;i&#39;</span><span class="p">,</span> <span class="s">&#39;o&#39;</span><span class="p">,</span> <span class="s">&#39;u&#39;</span><span class="p">}</span> <span class="n">nvalue</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">count</span> <span class="o">=</span> <span class="mi">0</span> <span class="c"># how many consecutive consonants</span> <span class="n">pos</span> <span class="o">=</span> <span class="o">-</span><span class="mi">1</span> <span class="c"># position of the last substring of n consonants</span> <span class="k">for</span> <span class="n">i</span><span class="p">,</span> <span class="n">c</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">s</span><span class="p">):</span> <span class="k">if</span> <span class="n">c</span> <span class="ow">in</span> <span class="n">vowels</span><span class="p">:</span> <span class="n">count</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">else</span><span class="p">:</span> <span class="n">count</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">if</span> <span class="n">count</span> <span class="o">&gt;=</span> <span class="n">n</span><span class="p">:</span> <span class="n">pos</span> <span class="o">=</span> <span class="n">i</span> <span class="o">+</span> <span class="mi">2</span> <span class="o">-</span> <span class="n">n</span> <span class="k">if</span> <span class="n">pos</span> <span class="o">&gt;=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">nvalue</span> <span class="o">+=</span> <span class="n">pos</span> <span class="k">return</span> <span class="n">nvalue</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">name</span><span class="p">,</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solve</span><span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="nb">int</span><span class="p">(</span><span class="n">n</span><span class="p">))))</span></code></pre></div> <h2>Pogo</h2> This is a very clever solution from xiaowuc1 (translated from Java to Python). The idea is to calculate at first the maximum number of steps you need and then go from your target destination to the origin. How many steps do you need? In the `$i$` round, you will make `$i$` steps. You need at least `$x+y$` steps to get from `$(0|0)$` to `$(x|y)$`. This means, you need to solve `$\sum_{i=1}^n i = x + y$` for `$n$`. This is `$\frac{n^2 + n}{2} = x+y$`. You might also need to make one extra step if the parity of `$\frac{n^2 + n}{2}$` is not the same as `$x+y$`. You can calculate this with a simple loop (see code below). After you know the maximum number of steps, you can apply a greedy solution: Start from `$(x|y)$` and always go into the direction that is farer away from the origin. <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">calculateSteps</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span> <span class="n">s</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">dist</span> <span class="o">=</span> <span class="nb">abs</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="o">+</span> <span class="nb">abs</span><span class="p">(</span><span class="n">y</span><span class="p">)</span> <span class="k">while</span> <span class="p">(</span><span class="n">s</span><span class="o">**</span><span class="mi">2</span> <span class="o">+</span> <span class="n">s</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span> <span class="o">&lt;</span> <span class="n">dist</span> <span class="ow">or</span> <span class="p">((</span><span class="n">s</span><span class="o">**</span><span class="mi">2</span> <span class="o">+</span> <span class="n">s</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span> <span class="o">!=</span> <span class="n">dist</span><span class="o">%</span><span class="mi">2</span><span class="p">:</span> <span class="n">s</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">s</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; starting at (0|0) and going i steps, </span> <span class="sd"> how can you reach (x|y)? &quot;&quot;&quot;</span> <span class="n">s</span> <span class="o">=</span> <span class="n">calculateSteps</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">)</span> <span class="n">solution</span> <span class="o">=</span> <span class="s">&quot;&quot;</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">s</span><span class="p">,</span> <span class="mi">1</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="o">&gt;</span> <span class="nb">abs</span><span class="p">(</span><span class="n">y</span><span class="p">):</span> <span class="k">if</span> <span class="n">x</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">solution</span> <span class="o">+=</span> <span class="s">&quot;E&quot;</span> <span class="n">x</span> <span class="o">-=</span> <span class="n">i</span> <span class="k">else</span><span class="p">:</span> <span class="n">solution</span> <span class="o">+=</span> <span class="s">&quot;W&quot;</span> <span class="n">x</span> <span class="o">+=</span> <span class="n">i</span> <span class="k">else</span><span class="p">:</span> <span class="k">if</span> <span class="n">y</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">solution</span> <span class="o">+=</span> <span class="s">&quot;N&quot;</span> <span class="n">y</span> <span class="o">-=</span> <span class="n">i</span> <span class="k">else</span><span class="p">:</span> <span class="n">solution</span> <span class="o">+=</span> <span class="s">&quot;S&quot;</span> <span class="n">y</span> <span class="o">+=</span> <span class="n">i</span> <span class="k">return</span> <span class="n">solution</span><span class="p">[::</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">),</span><span class="nb">int</span><span class="p">(</span><span class="n">y</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solve</span><span class="p">(</span><span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">)))</span></code></pre></div> <h2>The Great Wall</h2> The following solution is not applicable for the large input set, but it works fine for the small one: <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">collections</span> <span class="kn">import</span> <span class="n">defaultdict</span> <span class="k">def</span> <span class="nf">prepareTribes</span><span class="p">(</span><span class="n">tribes</span><span class="p">):</span> <span class="n">tribeStack</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">tribe</span> <span class="ow">in</span> <span class="n">tribes</span><span class="p">:</span> <span class="k">for</span> <span class="n">attackNumber</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">tribe</span><span class="p">[</span><span class="s">&quot;ni&quot;</span><span class="p">]):</span> <span class="n">tribeStack</span><span class="o">.</span><span class="n">append</span><span class="p">({</span> <span class="s">&quot;day&quot;</span> <span class="p">:</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;di&quot;</span><span class="p">]</span><span class="o">+</span><span class="n">attackNumber</span><span class="o">*</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;delta_di&quot;</span><span class="p">],</span> <span class="s">&quot;west&quot;</span><span class="p">:</span><span class="mi">2</span><span class="o">*</span><span class="p">(</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;wi&quot;</span><span class="p">]</span><span class="o">+</span><span class="n">attackNumber</span><span class="o">*</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;delta_pi&quot;</span><span class="p">]),</span> <span class="s">&quot;east&quot;</span><span class="p">:</span><span class="mi">2</span><span class="o">*</span><span class="p">(</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;ei&quot;</span><span class="p">]</span><span class="o">+</span><span class="n">attackNumber</span><span class="o">*</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;delta_pi&quot;</span><span class="p">]),</span> <span class="s">&quot;height&quot;</span><span class="p">:</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;si&quot;</span><span class="p">]</span><span class="o">+</span><span class="n">attackNumber</span><span class="o">*</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;delta_si&quot;</span><span class="p">]</span> <span class="p">})</span> <span class="k">return</span> <span class="nb">sorted</span><span class="p">(</span><span class="n">tribeStack</span><span class="p">,</span> <span class="n">key</span><span class="o">=</span><span class="k">lambda</span> <span class="n">tribe</span><span class="p">:</span> <span class="n">tribe</span><span class="p">[</span><span class="s">&quot;day&quot;</span><span class="p">])</span> <span class="k">def</span> <span class="nf">runAttack</span><span class="p">(</span><span class="n">wall</span><span class="p">,</span> <span class="n">tribe</span><span class="p">):</span> <span class="n">increase</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">tribe</span><span class="p">[</span><span class="s">&quot;west&quot;</span><span class="p">],</span> <span class="n">tribe</span><span class="p">[</span><span class="s">&quot;east&quot;</span><span class="p">]</span> <span class="o">+</span> <span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">wall</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">&lt;</span> <span class="n">tribe</span><span class="p">[</span><span class="s">&quot;height&quot;</span><span class="p">]:</span> <span class="c"># wall-ee</span> <span class="n">increase</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;wallPos&quot;</span> <span class="p">:</span> <span class="n">i</span><span class="p">,</span> <span class="s">&quot;height&quot;</span> <span class="p">:</span> <span class="n">tribe</span><span class="p">[</span><span class="s">&quot;height&quot;</span><span class="p">]})</span> <span class="k">return</span> <span class="n">increase</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">tribes</span><span class="p">):</span> <span class="n">wall</span> <span class="o">=</span> <span class="n">defaultdict</span><span class="p">(</span><span class="nb">int</span><span class="p">)</span> <span class="n">tribeStack</span> <span class="o">=</span> <span class="n">prepareTribes</span><span class="p">(</span><span class="n">tribes</span><span class="p">)</span> <span class="c">#for tribe in tribeStack:</span> <span class="c"># print tribe[&quot;day&quot;], &quot;[&quot; + str(tribe[&quot;west&quot;]) + &quot;,&quot; + str(tribe[&quot;east&quot;])+&quot;]&quot;, tribe[&quot;height&quot;]</span> <span class="n">successes</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">increase</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span><span class="p">,</span> <span class="n">tribe</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">tribeStack</span><span class="p">):</span> <span class="n">increaseTmp</span> <span class="o">=</span> <span class="n">runAttack</span><span class="p">(</span><span class="n">wall</span><span class="p">,</span> <span class="n">tribe</span><span class="p">)</span> <span class="c">#print wall</span> <span class="c">#print tribe</span> <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">increaseTmp</span><span class="p">)</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">successes</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">increase</span> <span class="o">+=</span> <span class="n">increaseTmp</span> <span class="k">if</span> <span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="o">==</span><span class="nb">len</span><span class="p">(</span><span class="n">tribeStack</span><span class="p">)</span> <span class="ow">or</span> <span class="n">tribeStack</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">][</span><span class="s">&quot;day&quot;</span><span class="p">]</span> <span class="o">&gt;</span> <span class="n">tribe</span><span class="p">[</span><span class="s">&quot;day&quot;</span><span class="p">]:</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="n">increase</span><span class="p">:</span> <span class="k">if</span> <span class="n">wall</span><span class="p">[</span><span class="n">el</span><span class="p">[</span><span class="s">&quot;wallPos&quot;</span><span class="p">]]</span> <span class="o">&lt;</span> <span class="n">el</span><span class="p">[</span><span class="s">&quot;height&quot;</span><span class="p">]:</span> <span class="n">wall</span><span class="p">[</span><span class="n">el</span><span class="p">[</span><span class="s">&quot;wallPos&quot;</span><span class="p">]]</span> <span class="o">=</span> <span class="n">el</span><span class="p">[</span><span class="s">&quot;height&quot;</span><span class="p">]</span> <span class="k">return</span> <span class="n">successes</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">N</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="c"># Number of tribes attacking the wall</span> <span class="n">tribes</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">tribe</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="n">di</span><span class="p">,</span> <span class="n">ni</span><span class="p">,</span> <span class="n">wi</span><span class="p">,</span> <span class="n">ei</span><span class="p">,</span> <span class="n">si</span><span class="p">,</span> <span class="n">delta_di</span><span class="p">,</span> <span class="n">delta_pi</span><span class="p">,</span> <span class="n">delta_si</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)</span> <span class="n">tribes</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&quot;di&quot;</span><span class="p">:</span><span class="nb">int</span><span class="p">(</span><span class="n">di</span><span class="p">),</span> <span class="c"># the day of the tribe&#39;s first attack</span> <span class="s">&quot;ni&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">ni</span><span class="p">),</span> <span class="c"># the number of attacks from this tribe</span> <span class="s">&quot;wi&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">wi</span><span class="p">),</span> <span class="c"># the westmost </span> <span class="s">&quot;ei&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">ei</span><span class="p">),</span> <span class="c"># and eastmost points respectively of the Wall attacked on the first attack</span> <span class="s">&quot;si&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">si</span><span class="p">),</span> <span class="c"># the strength of the first attack</span> <span class="s">&quot;delta_di&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">delta_di</span><span class="p">),</span> <span class="c"># the number of days between subsequent attacks by this tribe</span> <span class="s">&quot;delta_pi&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">delta_pi</span><span class="p">),</span> <span class="c"># the distance this tribe travels to the east between subsequent attacks (if this is negative, the tribe travels to the west)</span> <span class="s">&quot;delta_si&quot;</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">delta_si</span><span class="p">)</span> <span class="c"># the change in strength between subsequent attacks</span> <span class="p">})</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solve</span><span class="p">(</span><span class="n">tribes</span><span class="p">)))</span></code></pre></div> By the way, nobody has solved the large input set of this one with Python! But here is a <a href="http://www.go-hero.net/jam/13/name/eatmore">Java solution</a>. </li></ul> How do hash functions work? //martin-thoma.com/how-do-hash-functions-work/ Sat, 11 May 2013 20:07:07 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-do-hash-functions-work <p>Everybody who has written a noticeable amount of Java code should know the method <code><a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Object.html#hashCode()">hashCode</a>()</code>. But most beginners have difficulties to understand the significance of this little method. The following article gives you one small example with some impressions how much hash functions influence execution time.</p> <h2>Connect four</h2> <blockquote>Connect Four [...] is a two-player game in which the players first choose a color and then take turns dropping colored discs from the top into a seven-column, six-row vertically-suspended grid. The pieces fall straight down, occupying the next available space within the column. The object of the game is to connect four of one's own discs of the same color next to each other vertically, horizontally, or diagonally before your opponent. </blockquote> <p><small>Source: <a href="http://en.wikipedia.org/wiki/Connect_Four">Wikipedia</a></small></p> <p>It looks like this:</p> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2013/05/connect-four.gif"><img src="../images/2013/05/connect-four.gif" alt="Connect Four" width="" height="" class="size-full wp-image-65311" /></a><p class="wp-caption-text">Connect Four<br />Source: <a href="http://commons.wikimedia.org/wiki/File:Connect_Four.gif">commons.wikimedia.org</a></p></div> <h2>The task</h2> <p>Imagine you would like to find a good strategy where to drop your disk. A simple brute-force method is to create a so called <a href="http://en.wikipedia.org/wiki/Game_tree">game tree</a>. This means you go through each possibility at each situation that could occur in the game for both players.</p> <p>This approach has generally two problems:</p> <ol> <li>You have to know how to go through each situation. For connect four it is easy. Both players place their disks in turns and in every turn the current player has at most 7 possibilities. But it is impossible for games like <a href="http://en.wikipedia.org/wiki/Calvinball#Calvinball">Calvinball</a> or <a href="http://en.wikipedia.org/wiki/Mao_(card_game)">Mao</a>.</li> <li>The game tree might be HUGE. In this case, you can have `$4,531,985,219,092 \approx 4.5 \cdot 10^{12}$` game situations (<a href="http://math.stackexchange.com/a/301128/6876">source</a>). Even if you would need only one bit for each situation, it would require 566.5 GB!</li> </ol> <p>Anyway, lets say we want to store many unique game situations. Unique means, even if you have hundreds of possible paths to get to a given game situations, you will store this game situation only once.</p> <h2>Implementation</h2> <p>First of all, I would like to mention that you can <a href="#How_is_this_realated_to_hash_functions">skip the source code</a>. I’ve only included it to make it easier to understand what I’m talking about.</p> <p>Lets say our game situation looks like this:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="k">struct</span> <span class="n">gamesituation</span> <span class="p">{</span> <span class="cm">/** How does the board currently look like? */</span> <span class="kt">char</span> <span class="n">board</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">];</span> <span class="cm">/**</span> <span class="cm"> * What are the next game situations that I can reach from this </span> <span class="cm"> * board? </span> <span class="cm"> * The next[i] means that the player dropped the disc at column i</span> <span class="cm"> */</span> <span class="kt">int</span> <span class="n">next</span><span class="p">[</span><span class="mi">7</span><span class="p">];</span> <span class="cm">/* I could use a bitfield for this ... but it would make access</span> <span class="cm"> * much more inconvenient. </span> <span class="cm"> */</span> <span class="kt">unsigned</span> <span class="kt">char</span> <span class="n">isEmpty</span><span class="p">;</span> <span class="c1">// Is this gamesitatution already filled?</span> <span class="kt">unsigned</span> <span class="kt">char</span> <span class="n">isFinished</span><span class="p">;</span> <span class="c1">// Is this game finished?</span> <span class="kt">unsigned</span> <span class="kt">char</span> <span class="n">stalemate</span><span class="p">;</span> <span class="c1">// Was this game a stalemate?</span> <span class="kt">unsigned</span> <span class="kt">char</span> <span class="n">winRed</span><span class="p">;</span> <span class="c1">// Did red win?</span> <span class="kt">unsigned</span> <span class="kt">char</span> <span class="n">winBlack</span><span class="p">;</span> <span class="c1">// Did black win?</span> <span class="p">};</span></code></pre></div> <p>You need a check if one player won:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cm">/*</span> <span class="cm"> * Check if player has won by placing a disc on (x,y). </span> <span class="cm"> * with direction (xDir, yDir)</span> <span class="cm"> * @return 1 iff RED won, -1 iff BLACK won and 0 if nobody won</span> <span class="cm"> */</span> <span class="kt">signed</span> <span class="kt">char</span> <span class="nf">hasPlayerWon</span><span class="p">(</span><span class="kt">char</span> <span class="n">board</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">],</span> <span class="kt">int</span> <span class="n">x</span><span class="p">,</span> <span class="kt">int</span> <span class="n">y</span><span class="p">,</span> <span class="kt">char</span> <span class="n">xDir</span><span class="p">,</span> <span class="kt">char</span> <span class="n">yDir</span><span class="p">)</span> <span class="p">{</span> <span class="kt">char</span> <span class="n">color</span> <span class="o">=</span> <span class="n">board</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">];</span> <span class="kt">int</span> <span class="n">tokensInRow</span> <span class="o">=</span> <span class="n">getTokensInRow</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">color</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">xDir</span><span class="p">,</span> <span class="n">yDir</span><span class="p">)</span> <span class="o">+</span> <span class="n">getTokensInRow</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">color</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="o">-</span><span class="n">xDir</span><span class="p">,</span> <span class="o">-</span><span class="n">yDir</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">tokensInRow</span> <span class="o">&gt;=</span> <span class="n">WINNING_NR</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">color</span> <span class="o">==</span> <span class="n">RED</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="k">if</span> <span class="p">(</span><span class="n">color</span> <span class="o">==</span> <span class="n">BLACK</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="o">-</span><span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">perror</span><span class="p">(</span><span class="s">&quot;this color doesn&#39;t / shouldn&#39;t exist</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="n">exit</span><span class="p">(</span><span class="mi">1</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span> <span class="cm">/* </span> <span class="cm"> * A new disc has been dropped. Check if this disc means that </span> <span class="cm"> * somebody won.</span> <span class="cm"> * @return 1 iff RED won, -1 iff BLACK won, otherwise NOT_FINISHED</span> <span class="cm"> */</span> <span class="kt">int</span> <span class="nf">isBoardFinished</span><span class="p">(</span><span class="kt">char</span> <span class="n">board</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">],</span> <span class="kt">int</span> <span class="n">x</span><span class="p">,</span> <span class="kt">int</span> <span class="n">y</span><span class="p">)</span> <span class="p">{</span> <span class="kt">signed</span> <span class="kt">char</span> <span class="n">status</span><span class="p">;</span> <span class="c1">// check left-right</span> <span class="n">status</span> <span class="o">=</span> <span class="n">hasPlayerWon</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">status</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">status</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// top-down</span> <span class="n">status</span> <span class="o">=</span> <span class="n">hasPlayerWon</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">status</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">status</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// down-left to top-right</span> <span class="n">status</span> <span class="o">=</span> <span class="n">hasPlayerWon</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">status</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">status</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// top-left to down-right</span> <span class="n">status</span> <span class="o">=</span> <span class="n">hasPlayerWon</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">status</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">status</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">NOT_FINISHED</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>If you need an explanation for this, you should read <a href="../check-x-in-a-row-for-board-games/" title="Check x-in-a-row for board games">this article</a>.</p> <p>And you need a function that can mirror boards (to get rid of identical, but mirrored situations) and one that can compare boards:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="kt">char</span> <span class="nf">isSameBoard</span><span class="p">(</span><span class="kt">char</span> <span class="n">a</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">],</span> <span class="kt">char</span> <span class="n">b</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">])</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">x</span> <span class="o">&lt;</span> <span class="n">BOARD_WIDTH</span><span class="p">;</span> <span class="n">x</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">y</span> <span class="o">&lt;</span> <span class="n">BOARD_HEIGHT</span><span class="p">;</span> <span class="n">y</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">a</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">]</span> <span class="o">!=</span> <span class="n">b</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">])</span> <span class="p">{</span> <span class="k">return</span> <span class="n">FALSE</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="n">TRUE</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">mirrorBoard</span><span class="p">(</span><span class="kt">char</span> <span class="n">board</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">],</span> <span class="kt">char</span> <span class="n">newBoard</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">])</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">x</span> <span class="o">&lt;</span> <span class="n">BOARD_WIDTH</span><span class="p">;</span> <span class="n">x</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">y</span> <span class="o">&lt;</span> <span class="n">BOARD_HEIGHT</span><span class="p">;</span> <span class="n">y</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">newBoard</span><span class="p">[</span><span class="n">BOARD_WIDTH</span> <span class="o">-</span> <span class="n">x</span> <span class="o">-</span> <span class="mi">1</span><span class="p">][</span><span class="n">y</span><span class="p">]</span> <span class="o">=</span> <span class="n">board</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span></code></pre></div> <p>You need a function that makes all possible moves for the players:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cm">/*</span> <span class="cm"> * Make all possible turns that the player can make in this</span> <span class="cm"> * game situation.</span> <span class="cm"> */</span> <span class="kt">void</span> <span class="nf">makeTurns</span><span class="p">(</span><span class="kt">char</span> <span class="n">board</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">],</span> <span class="kt">char</span> <span class="n">currentPlayer</span><span class="p">,</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">lastId</span><span class="p">,</span> <span class="kt">int</span> <span class="n">recursion</span><span class="p">)</span> <span class="p">{</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">insertID</span><span class="p">;</span> <span class="kt">int</span> <span class="n">outcome</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">column</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">column</span> <span class="o">&lt;</span> <span class="n">BOARD_WIDTH</span><span class="p">;</span> <span class="n">column</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// add to column</span> <span class="kt">int</span> <span class="n">height</span> <span class="o">=</span> <span class="n">BOARD_HEIGHT</span> <span class="o">-</span> <span class="mi">1</span><span class="p">;</span> <span class="c1">// the disc falls down</span> <span class="k">while</span> <span class="p">(</span><span class="n">height</span> <span class="o">&gt;=</span> <span class="mi">0</span> <span class="o">&amp;&amp;</span> <span class="n">board</span><span class="p">[</span><span class="n">column</span><span class="p">][</span><span class="n">height</span><span class="p">]</span> <span class="o">==</span> <span class="n">EMPTY</span><span class="p">)</span> <span class="p">{</span> <span class="n">height</span><span class="o">--</span><span class="p">;</span> <span class="p">}</span> <span class="n">height</span><span class="o">++</span><span class="p">;</span> <span class="c1">// this colum is full</span> <span class="k">if</span> <span class="p">(</span><span class="n">height</span> <span class="o">==</span> <span class="mi">6</span><span class="p">)</span> <span class="p">{</span> <span class="k">continue</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// place disc</span> <span class="n">board</span><span class="p">[</span><span class="n">column</span><span class="p">][</span><span class="n">height</span><span class="p">]</span> <span class="o">=</span> <span class="n">currentPlayer</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">didBoardAlreadyOccur</span><span class="p">(</span><span class="n">board</span><span class="p">))</span> <span class="p">{</span> <span class="c1">// I&#39;ve already got to this situation</span> <span class="n">insertID</span> <span class="o">=</span> <span class="n">getBoardIndex</span><span class="p">(</span><span class="n">board</span><span class="p">);</span> <span class="n">savePreviousID</span><span class="p">(</span><span class="n">insertID</span><span class="p">,</span> <span class="n">lastId</span><span class="p">,</span> <span class="n">column</span><span class="p">);</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="kt">char</span> <span class="n">mirrored</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">];</span> <span class="n">mirrorBoard</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">mirrored</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">didBoardAlreadyOccur</span><span class="p">(</span><span class="n">mirrored</span><span class="p">))</span> <span class="p">{</span> <span class="c1">// I&#39;ve already got this situation, but mirrored</span> <span class="c1">// so take care of symmetry at this point</span> <span class="n">mirroredCounter</span><span class="o">++</span><span class="p">;</span> <span class="n">insertID</span> <span class="o">=</span> <span class="n">getBoardIndex</span><span class="p">(</span><span class="n">mirrored</span><span class="p">);</span> <span class="n">savePreviousID</span><span class="p">(</span><span class="n">insertID</span><span class="p">,</span> <span class="n">lastId</span><span class="p">,</span> <span class="n">column</span><span class="p">);</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">registeredSituations</span><span class="o">++</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">registeredSituations</span> <span class="o">==</span> <span class="n">MAXIMUM_SITUATIONS</span><span class="p">)</span> <span class="p">{</span> <span class="n">giveCurrentInformation</span><span class="p">();</span> <span class="n">exit</span><span class="p">(</span><span class="n">MAXIMUM_SITUATIONS_REACHED_EXIT_STATUS</span><span class="p">);</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="n">REGISTERED_MOD</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="o">&amp;&amp;</span> <span class="n">registeredSituations</span> <span class="o">%</span> <span class="n">REGISTERED_MOD</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">giveCurrentInformation</span><span class="p">();</span> <span class="p">}</span> <span class="n">outcome</span> <span class="o">=</span> <span class="n">isBoardFinished</span><span class="p">(</span><span class="n">board</span><span class="p">,</span> <span class="n">column</span><span class="p">,</span> <span class="n">height</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">ABS</span><span class="p">(</span><span class="n">outcome</span><span class="p">)</span> <span class="o">&lt;=</span> <span class="mi">1</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// the game is finished</span> <span class="n">insertID</span> <span class="o">=</span> <span class="n">getNewIndex</span><span class="p">(</span><span class="n">board</span><span class="p">);</span> <span class="n">storeToDatabase</span><span class="p">(</span><span class="n">insertID</span><span class="p">,</span> <span class="n">board</span><span class="p">,</span> <span class="n">TRUE</span><span class="p">,</span> <span class="n">outcome</span><span class="p">);</span> <span class="n">savePreviousID</span><span class="p">(</span><span class="n">insertID</span><span class="p">,</span> <span class="n">lastId</span><span class="p">,</span> <span class="n">column</span><span class="p">);</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="c1">// Switch players</span> <span class="k">if</span> <span class="p">(</span><span class="n">currentPlayer</span> <span class="o">==</span> <span class="n">RED</span><span class="p">)</span> <span class="p">{</span> <span class="n">currentPlayer</span> <span class="o">=</span> <span class="n">BLACK</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">currentPlayer</span> <span class="o">=</span> <span class="n">RED</span><span class="p">;</span> <span class="p">}</span> <span class="n">insertID</span> <span class="o">=</span> <span class="n">getNewIndex</span><span class="p">(</span><span class="n">board</span><span class="p">);</span> <span class="n">setBoard</span><span class="p">(</span><span class="n">insertID</span><span class="p">,</span> <span class="n">board</span><span class="p">);</span> <span class="n">savePreviousID</span><span class="p">(</span><span class="n">insertID</span><span class="p">,</span> <span class="n">lastId</span><span class="p">,</span> <span class="n">column</span><span class="p">);</span> <span class="kt">char</span> <span class="n">copy</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">];</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">x</span> <span class="o">&lt;</span> <span class="n">BOARD_WIDTH</span><span class="p">;</span> <span class="n">x</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">y</span> <span class="o">&lt;</span> <span class="n">BOARD_HEIGHT</span><span class="p">;</span> <span class="n">y</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">copy</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">]</span> <span class="o">=</span> <span class="n">board</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="n">makeTurns</span><span class="p">(</span><span class="n">copy</span><span class="p">,</span> <span class="n">currentPlayer</span><span class="p">,</span> <span class="n">insertID</span><span class="p">,</span> <span class="n">recursion</span> <span class="o">+</span> <span class="mi">1</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span></code></pre></div> <h2>How is this realated to hash functions?</h2> <p>You might have noticed a few functions that I didn’t explain by now:</p> <ul> <li><code>didBoardAlreadyOccur(board)</code>: Checks if a given board is stored in database.</li> <li><code>getBoardIndex(board)</code>: This is a function that takes a board and gives a non-negative integer which is characteristic for the given board.</li> <li><code>savePreviousID(insertID, lastId, column)</code>: store insertID as a possible next situation for lastId in database</li> <li><code>setBoard(insertID, board)</code>: Insert board into database at position insertID</li> </ul> <p>How would you implement <code>didBoardAlreadyOccur(board)</code>? This function (or insertID) will be the slowest part of the code and will be called VERY often. So it needs to be as fast as possible.</p> <h2>A hash function</h2> <p>Most of the time you can create hash functions by mapping values to integers. In my case, I mapped the board - which is a two-dimensional char array - to one integer by thinking of it as a very long number. I think of a red disc as the digit 1, a black disc as the digit 2 and an empty field as 0:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="kt">unsigned</span> <span class="kt">int</span> <span class="nf">charToInt</span><span class="p">(</span><span class="kt">char</span> <span class="n">x</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">x</span> <span class="o">==</span> <span class="n">RED</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="k">if</span> <span class="p">(</span><span class="n">x</span> <span class="o">==</span> <span class="n">BLACK</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="mi">2</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span></code></pre></div> <p>When you want to get the board number, you can get it like this:</p> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2013/05/connect-four-to-number.png"><img src="../images/2013/05/connect-four-to-number.png" alt="Empty=0, red=1, yellow=2" width="" height="" class="size-full wp-image-65761" /></a><p class="wp-caption-text">Empty=0, red=1, yellow=2<br />The board number is 00000000000000000210000211210112212</p></div> <p>For most game situations, this number will be much too big to store it in an integer. Also, we would like to get an index for our array so that we know where to store this board. The simplest solution to this problem is to calculate <code>NUMBER % ARRAY_SIZE</code>:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="kt">unsigned</span> <span class="kt">int</span> <span class="nf">getFirstIndex</span><span class="p">(</span><span class="kt">char</span> <span class="n">board</span><span class="p">[</span><span class="n">BOARD_WIDTH</span><span class="p">][</span><span class="n">BOARD_HEIGHT</span><span class="p">])</span> <span class="p">{</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">index</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">x</span> <span class="o">&lt;</span> <span class="n">BOARD_WIDTH</span><span class="p">;</span> <span class="n">x</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">y</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">y</span> <span class="o">&lt;</span> <span class="n">BOARD_HEIGHT</span><span class="p">;</span> <span class="n">y</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">index</span> <span class="o">+=</span> <span class="n">charToInt</span><span class="p">(</span><span class="n">board</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">])</span> <span class="o">*</span> <span class="n">myPow</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span> <span class="p">((</span><span class="n">x</span> <span class="o">+</span> <span class="n">y</span> <span class="o">*</span> <span class="n">BOARD_WIDTH</span><span class="p">)</span> <span class="o">%</span> <span class="n">HASH_MODULO</span><span class="p">));</span> <span class="p">}</span> <span class="p">}</span> <span class="n">index</span> <span class="o">=</span> <span class="n">index</span> <span class="o">%</span> <span class="n">MAXIMUM_SITUATIONS</span><span class="p">;</span> <span class="k">return</span> <span class="n">index</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>The function <code>getFirstIndex</code> maps an char Array with BOARD_WIDTH * BOARD_HEIGHT = 7 * 6 = 42 elements to an integer interval [0, MAXIMUM_SITUATIONS] = [0, 20000000]. Although I only use three values for the char array, that is <code>$3^{42} = 109418989131512359209 \approx 1.09 \cdot 10^{20}$</code>. There are many game situation numbers that can never occur (e.g. two more red than black dists), but we still map a significantly larger space to [0,20000000]. You can’t change that. You can probably find (much) better mappings, but as we know that there are <code>$4.5 \cdot 10^{12}$</code> game situations, you will always have the problem that your codomain is much smaller than the domain of your hash function. That’s a fundamental problem of hash functions.</p> <p>This means, you will have two board situations that map to the same hash number. This is called a “hash collision”. When you use the hash number directly as an index for your board, you will have to deal with hash collisions. Some solutions are:</p> <ul> <li>Ignoring the problem: That's boring and not always possible (but simple).</li> <li>Linear probing</li> <li>Quadratic probing</li> </ul> <h2>Linear probing</h2> <p>The idea of linear probing is very simple:</p> <p>Inserting a new item:</p> <ol> <li>You look at the index `$i$` that your hash function gave you.</li> <li>If this index is already full, you look at `$i+1$`</li> <li>When you took a look at all slots of your array, you can't insert the new item.</li> </ol> <p>Searching for an already inserted item:</p> <ol> <li>You look at the index `$i$` that your hash function gave you.</li> <li>If `$i$` is empty, you're ready. The item was not inserted.</li> <li>If `$i$` is not the item you've searched for, you have to look at `$i+1$`.</li> <li>Keep looking at the next item until you find your searched item, you've looked at all items or you find an empty slot.</li> </ol> <p>Deleting is complicated. You have to look at all items after the deleted one, remove them from your array and insert them again. That’s not good.</p> <p>The problem of linear probing is <strong>clustering</strong>. When you have some hash values that are close together, you might get hash collisions faster. When you’ve got your first collisions, you resolve them by inserting the value close to the value where you originally wanted to save it. So you get one big cluster quite fast. When you want to insert an element in the cluster, you first have to search the end of the cluster. That’s bad for performance.</p> <p>An advantage of linear probing compared to quadratic probing is that you might get a better performance due to cache effects.</p> <h2>Quadratic probing</h2> <p>The idea of quadratic probing is the same as for linear probing, but you try to fix the clustering-problem by using a clever way to search for a free spot:</p> <p><code>$h_i(x) = \left(h(x) + (-1)^{i+1} \cdot \left\lceil\frac{i}{2}\right\rceil^2\right) \bmod~m$</code></p> <p>where <code>$h$</code> is your hash function and <code>$i$</code> is your i-th try to find a free spot while you have <code>$m$</code> spots in total.</p> <p>This one also suffers from clustering, but it’s not as bad as with linear clustering.</p> <h2>Double hashing</h2> <p>This solution could be the best one, but also the hardest one to implement correctly. You could find a free spot by using a second hash function <code>$h'$</code> like this:</p> <p><code>$h_i(x) = (h(x)+h'(x)\cdot i) ~ \bmod ~ m$</code></p> <p>BUT you have to make sure that <code>$Pr[h(x)=h(y) \land h'(x)=h'(y)] = \frac{1}{m^2}$</code></p> <h2>Performance</h2> <p>You can use linear probing, quadratic probing and double hashing in my example and measure how many game situations get stored. The more game situations you can store in the same amount of time, the better:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/connectfour-probing.png"><img src="../images/2013/05/connectfour-probing.png" alt="Linear probing, quadratic probing and double hashing for connect four" width="" height="" class="size-full wp-image-65871" /></a><p class="wp-caption-text">Linear probing, quadratic probing and double hashing for connect four</p></div> <p>You can see that linear probing performs much worse than quadratic probing and double hashing. When you compare quadratic probing with double hashing, there seems not to be a big difference. But note that my second hash function is almost the same as the first one. You could probably choose a better second hash function and get better results (suggestions are welcome).</p> <h2>Why are hash functions important?</h2> <p>Hash functions help you to map a big amount of data to a small space. They are important, because they are a relevant part of many datastructures. The better they are, the faster will operations on those datastructures work. Better means: Faster to compute or less collisions.</p> <p>Some datastructures like this are:</p> <ul> <li><a href="http://docs.oracle.com/javase/7/docs/api/java/util/HashMap.html">HashMap</a> and <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Hashtable.html">HashTable</a> (&rarr; <a href="http://stackoverflow.com/a/40878/562769">difference</a>)</li> <li><a href="http://docs.oracle.com/javase/7/docs/api/java/util/HashSet.html">HashSet</a></li> </ul> <h2>Final notes</h2> <p>Another resolution for hash collisions is creating a linked list. This means you will not suffer from clustering and you can insert in <code>$\mathcal{O}(1)$</code>. But searching for an element is still in <code>$\mathcal{O}(n)$</code>, where <code>$n$</code> is the number of elements that were already inserted.</p> <h2>Resources</h2> <p>You can find the <a href="https://github.com/MartinThoma/connect-four/tree/master/C">code at GitHub</a>.</p> Google Code Jam – Round 1B 2013 //martin-thoma.com/google-code-jam-round-1b-2013/ Sun, 05 May 2013 16:15:32 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-round-1b-2013 <ul> <li>Problem A (<a href="https://code.google.com/codejam/contest/2434486/dashboard#s=p0">Osmos</a>): <ul> <li>Small Set: 4668/7250 users (64%)</li> <li>Large Set: 3537/4578 users (77%)</li> </ul> <li>Problem B (<a href="https://code.google.com/codejam/contest/2434486/dashboard#s=p1">Falling Diamonds</a>): <ul> <li>Small Set: 952/1882 users (51%)</li> <li>Large Set: 525/724 users (73%)</li> </ul> </li> <li>Problem C (<a href="https://code.google.com/codejam/contest/2434486/dashboard#s=p2">Garbled Email</a>): <ul> <li>Small Set: 444/896 users (50%)</li> <li>Large Set: 255/345 users (74%)</li> </ul> </li> More information are on <a href="http://www.go-hero.net/jam/13/round/2">go-hero.net</a>. <h2>Osmos</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">howBigDoIget</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">):</span> <span class="k">while</span> <span class="nb">len</span><span class="p">(</span><span class="n">motes</span><span class="p">)</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">A</span> <span class="o">&gt;</span> <span class="nb">min</span><span class="p">(</span><span class="n">motes</span><span class="p">):</span> <span class="n">A</span> <span class="o">+=</span> <span class="nb">min</span><span class="p">(</span><span class="n">motes</span><span class="p">)</span> <span class="n">motes</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="nb">min</span><span class="p">(</span><span class="n">motes</span><span class="p">))</span> <span class="k">return</span> <span class="n">A</span> <span class="k">def</span> <span class="nf">stepsNeededForNext</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">):</span> <span class="n">m</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="n">motes</span><span class="p">)</span> <span class="n">steps</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">if</span> <span class="n">m</span> <span class="o">&gt;=</span> <span class="mi">1</span> <span class="ow">and</span> <span class="n">A</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="mi">10</span><span class="o">**</span><span class="mi">12</span> <span class="k">while</span> <span class="n">A</span> <span class="o">&lt;=</span> <span class="n">m</span><span class="p">:</span> <span class="n">A</span> <span class="o">+=</span> <span class="p">(</span><span class="n">A</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="n">steps</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">steps</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">):</span> <span class="n">steps</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">A</span> <span class="o">=</span> <span class="n">howBigDoIget</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">)</span> <span class="k">while</span> <span class="nb">len</span><span class="p">(</span><span class="n">motes</span><span class="p">)</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">A</span> <span class="o">&lt;=</span> <span class="nb">max</span><span class="p">(</span><span class="n">motes</span><span class="p">):</span> <span class="k">if</span> <span class="p">(</span><span class="n">stepsNeededForNext</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">)</span> <span class="o">&gt;=</span> <span class="nb">len</span><span class="p">(</span><span class="n">motes</span><span class="p">)):</span> <span class="n">steps</span> <span class="o">+=</span> <span class="nb">len</span><span class="p">(</span><span class="n">motes</span><span class="p">)</span> <span class="k">return</span> <span class="n">steps</span> <span class="k">else</span><span class="p">:</span> <span class="n">A</span> <span class="o">+=</span> <span class="p">(</span><span class="n">A</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="n">A</span> <span class="o">=</span> <span class="n">howBigDoIget</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">)</span> <span class="n">steps</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">steps</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">A</span><span class="p">,</span> <span class="n">N</span> <span class="o">=</span> <span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span><span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">))</span> <span class="n">motes</span> <span class="o">=</span> <span class="nb">sorted</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span><span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)))</span> <span class="n">copyed</span> <span class="o">=</span> <span class="n">motes</span><span class="p">[:]</span> <span class="n">solution</span> <span class="o">=</span> <span class="n">solve</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">motes</span><span class="p">)</span> <span class="k">if</span> <span class="n">solution</span> <span class="o">&gt;</span> <span class="n">N</span><span class="p">:</span> <span class="n">solution</span> <span class="o">=</span> <span class="n">N</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solution</span><span class="p">))</span></code></pre></div> <h2>Falling Diamonds</h2> Oncee you've read the task, you should understand some very basic ideas: <ul> <li>First of all, diamonds only fall at `$x=0$`!</li> <li>If your target coordinates are `$(x,y)$`, you have the same output as for `$(-x,y)$`, as everything is symmetric.</li> <li>You have to get a basis for your diamonds pyramid. I've colored the basis in yellow in the images below.</li> <li>When your target is above the ground, you can let the diamond slide down to calculate the size of the basis.</li> </ul> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/falling-diamonds-base.jpg"><img src="../images/2013/05/falling-diamonds-base.jpg" alt="A basis for diamonds" width="" height="" class="size-full wp-image-65431" /></a><p class="wp-caption-text">You have to get those yellow diamonds first, before you can get the orange one.</p></div> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/05/falling-diamonds-slide.jpg"><img src="../images/2013/05/falling-diamonds-slide.jpg" alt="Let Diamonds slide down" width="" height="" class="size-full wp-image-65441" /></a><p class="wp-caption-text">Let Diamonds slide down</p></div> Note that you don't have to calculate a probabilty for the yellow pyramids. You get those with probability of 1. What I've forgot: You should also catch the case that you can fill up the next bigger pyramid. If this is possible, you can guarantee that you will reach your target `$(x,y)$`. The rest is simple math. You have `$rest$` diamonds left after you've build the base (yellow). Then you need `$y+1$` diamonds slide to the right side. The probability that you have exactly `$k$` hits while making `$N$` tries with a probability of 50% is `$\binom{N}{k} \cdot (\frac{1}{2})^N$`. You want at least `$k$` hits, so you want `$\sum_{i=k}^N \binom{N}{i} \cdot (\frac{1}{2})^N$`. <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">gmpy</span> <span class="sd">&quot;&quot;&quot; Calculate the binomial coefficient &quot;&quot;&quot;</span> <span class="k">def</span> <span class="nf">binomial</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">k</span><span class="p">):</span> <span class="k">return</span> <span class="n">gmpy</span><span class="o">.</span><span class="n">comb</span><span class="p">(</span><span class="n">n</span><span class="p">,</span><span class="n">k</span><span class="p">)</span> <span class="sd">&quot;&quot;&quot; </span> <span class="sd"> @param N: Number of diamonds</span> <span class="sd"> @param x,y: Target coordinate</span> <span class="sd"> @return: possiblity, that a diamond will be at coordinate (x,y) </span> <span class="sd">&quot;&quot;&quot;</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">N</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span> <span class="k">if</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">n</span> <span class="o">=</span> <span class="n">y</span><span class="o">+</span><span class="mi">1</span> <span class="k">if</span> <span class="n">N</span> <span class="o">&gt;=</span> <span class="p">(</span><span class="n">n</span><span class="o">*</span><span class="n">n</span><span class="o">+</span><span class="n">n</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span><span class="p">:</span> <span class="k">return</span> <span class="mf">1.0</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="mf">0.0</span> <span class="c"># From this point, x != 0 is True</span> <span class="n">xTmp</span> <span class="o">=</span> <span class="n">x</span> <span class="o">+</span> <span class="n">y</span> <span class="c"># let target slide down</span> <span class="n">n</span> <span class="o">=</span> <span class="n">xTmp</span><span class="o">-</span><span class="mi">1</span> <span class="n">baseDiamands</span> <span class="o">=</span> <span class="p">(</span><span class="n">n</span><span class="o">**</span><span class="mi">2</span><span class="o">+</span><span class="n">n</span><span class="p">)</span><span class="o">/</span><span class="mi">2</span> <span class="c"># are there enough diamonds left after you&#39;ve build the basis?</span> <span class="n">rest</span> <span class="o">=</span> <span class="n">N</span> <span class="o">-</span> <span class="n">baseDiamands</span> <span class="k">if</span> <span class="n">rest</span> <span class="o">&lt;=</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="mf">0.0</span> <span class="c"># are there enough diamonds left so that you can guarantee that </span> <span class="c"># you will fill up the next bigger pyramid at least to the </span> <span class="c"># target position?</span> <span class="n">biggerBaseDiamonds</span> <span class="o">=</span> <span class="n">baseDiamands</span><span class="o">+</span><span class="n">n</span><span class="o">+</span><span class="mi">2</span><span class="o">+</span><span class="n">y</span> <span class="k">if</span> <span class="n">N</span> <span class="o">&gt;=</span> <span class="n">biggerBaseDiamonds</span><span class="p">:</span> <span class="k">return</span> <span class="mf">1.0</span> <span class="c"># some math:</span> <span class="c"># bernoulli</span> <span class="n">prob</span> <span class="o">=</span> <span class="mf">0.0</span> <span class="n">hitsNeeded</span> <span class="o">=</span> <span class="n">y</span><span class="o">+</span><span class="mi">1</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">hitsNeeded</span><span class="p">,</span> <span class="n">rest</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">prob</span> <span class="o">+=</span> <span class="n">binomial</span><span class="p">(</span><span class="n">rest</span><span class="p">,</span><span class="n">k</span><span class="p">)</span> <span class="k">return</span> <span class="n">prob</span><span class="o">/</span><span class="mi">2</span><span class="o">**</span><span class="n">rest</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">N</span><span class="p">,</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span> <span class="o">=</span> <span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span><span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%.9Lf</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solve</span><span class="p">(</span><span class="n">N</span><span class="p">,</span> <span class="nb">abs</span><span class="p">(</span><span class="n">x</span><span class="p">),</span> <span class="n">y</span><span class="p">)))</span></code></pre></div> </li></ul> Sicherheit-Klausur //martin-thoma.com/sicherheit-klausur/ Mon, 29 Apr 2013 10:19:05 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sicherheit-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Sicherheit&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn <a href="http://www.iks.kit.edu/index.php?id=hofheinz">Jun.-Prof. Hofheinz</a> im Sommersemester 2013 gehört.</div> <p>An diesem Artikel wird natürlich noch gearbeitet.</p> <h2>Behandelter Stoff</h2> <table> <tr> <td>25.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Caesar, Vigenere, One-Time-Pad</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL01.pdf">VL 01</a></td> </tr> <tr> <td>22.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Symmetrische Verschlüsselungen; Stromchiffren; Blockchiffren (DES, AES); <span class="hint" title="ECB, CBC, CFB, OFB"><a href="http://commons.wikimedia.org/wiki/User:MartinThoma#Betriebsmodi">Betriebsmodi</a></span>: <table> <tr> <th rowspan="2">Modus</th> <th rowspan="2">Verschlüsselung<br />Entschlüsselung</th> <th colspan="2">Parallelisierbarkeit</th> </tr> <tr> <th>verschl.</th> <th>entschl.</th> </tr> <tr> <td>ECB</td> <td>`$c_i = ENC(K, m_i)$`<br />`$m_i = DEC(K, m_i)$`</td> <td>Ja</td> <td>Ja</td> </tr> <tr> <td>CBC</td> <td>`$c_i = ENC(K, m_i \oplus c_{i-1})$`<br />`$m_i = DEC(K, c_i) \oplus c_{i-1}$`</td> <td>Nein</td> <td>Ja</td> </tr> <tr> <td>CFB</td> <td>`$c_i = m_i \oplus ENC(K, c_{i-1})$`<br />`$m_i = c_i \oplus ENC(K, c_{i-1})$`</td> <td>Nein</td> <td>Ja</td> </tr> <tr> <td>OFB</td> <td>`$c_i = m_i \oplus ENC(K, IV)^i$`<br />`$m_i = c_i \oplus ENC(K, IV)^i$`</td> <td>Nein</td> <td>Nein</td> </tr> </table> <a href="http://commons.wikimedia.org/wiki/File:DES-main-network.png">DES-Feistelstruktur</a> </td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL02.pdf">VL 02</a></td> </tr> <tr> <td>25.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Lineare Kryptoanalyse, Differentielle Kryptoanalyse, <a href="../semantische-sicherheit/" title="Semantische Sicherheit">Semantische Sicherheit</a>, <a href="../sicherheit-klausur/#Fragen">IND-CPA</a>, Feistel-Schema</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL03.pdf">VL 03</a></td> </tr> <tr> <td>29.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;"><span class="hint" title="128 Bit, 160 Bit und 256 Bit hashes sind üblich">Hashfunktionen</span>, <a href="../kollisionsresistente-hashfunktionen-und-einwegfunktionen/">Kollisionsresistenz `$\Rightarrow$` Einwegeigenschaft</a>, <span class="hint" title="Beeinflusste MD5, SHA-1, SHA-2. SHA-3 benutzt MD nicht.">Merkle-Damgard-Konstruktion</span> und Length-Extension-Problematik, Birthday Attack, Meet-in-the-Middle-Angriff</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL04.pdf">VL 04</a></td> </tr> <tr> <td>06.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Public-Key-Verschlüsselung (Idee, RSA); Meet-in-the-Middle-Angriff für Hashfunktionen</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL05.pdf">VL 05</a></td> </tr> <tr> <td>13.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Rest Public-Key-Verschlüsselung (ElGamal, Vergleich RSA/ElGamal), Symmetrische Authentifikation von Nachrichten (Sicherheitsmodell, Hash-then-Sign, <abbr title="Pseudorandom functions">PRFs</abbr>, <abbr title="Hash-based message authentication code">HMAC</abbr>), <a href="http://de.wikipedia.org/wiki/Message_Authentication_Code">MAC</a></td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL06.pdf">VL 06</a></td> </tr> <tr> <td>27.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Asymmetrische Authentifikation von Nachrichten (RSA-PSS, ElGamal, DSA)</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL07.pdf">VL 07</a></td> </tr> <tr> <td>03.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Schlüsselaustausch (<span class="hint" title="Kommunikation über Key Center. Wichtig ist vor allem ein Zeitstempel.">Kerberos</span>, TLS, Angriffe)</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL08.pdf">VL 08</a></td> </tr> <tr> <td>10.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Schlüsselaustausch (TLS-Angriffe, weitere Verfahren), Identifikationsprotokolle</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL09.pdf">VL 09</a></td> </tr> <tr> <td>13.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Identifikationsprotokolle (Sicherheitsanalyse), Zero-Knowledge-Protokolle, Commitment &rarr; Hiding</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL10.pdf">VL 10</a></td> </tr> <tr> <td>17.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Zero-Knowledge-Protokolle, Nutzerauthentifikation</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL11.pdf">VL 11</a></td> </tr> <tr> <td>24.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Nutzerauthentifikation (Wörterbuchangriffe, interaktive Authentifikation, positionsbasierte Kryptographie); Rainbowtables; LM-Hashes</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL12.pdf">VL 12</a></td> </tr> <tr> <td>27.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Nutzerauthentifikation (positionsbasierte Kryptographie), Zugriffskontrolle (Bell-LaPadula)</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL13.pdf">VL 13</a></td> </tr> <tr> <td>01.07.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Zugriffskontrolle (Bell-LaPadula, Chinese Wall), Analyse grö&szlig;erer Systeme</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL14.pdf">VL 14</a></td> </tr> <tr> <td>08.07.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Analyse grö&szlig;erer Systeme, häufige Sicherheitsprobleme</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL15.pdf">VL 15</a></td> </tr> <tr> <td>11.07.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Häufige Sicherheitsprobleme</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL16.pdf">VL 16</a></td> </tr> </table> <p>Falls hier was fehlt, könnt ihr mich gerne in den Kommentaren oder per Mail (info@martin-thoma.de) darauf aufmerksam machen. Ich bin ja mal gespannt, ob ich das bis zum Ende aktuell halte.</p> <h2>Definitionen und Sätze</h2> <div class="definition"> Eine über `$k$` parametrisierte Funktion `$H$` ist <strong>kollisionsresistent</strong>, wenn jeder PPT-Algorithmus nur mit höchstens vernachlässigbarer Wahrscheinlichkeit eine Kollision findet. Für jeden PPT-Algorithmus `$\mathcal{A}$` ist `$Adv^{cr}_{H,\mathcal{A}}(k) := Pr[(X,X') \leftarrow \mathcal{A}(1^k): X \neq X' \land H_k(X) = H_k(X')]$` vernachlässigbar. </div> <div class="definition"> Eine über `$k$` parametrisierte Funktion `$H$` ist eine <strong>Einwegfunktion</strong> bzgl. der Urbildverteilung `$\mathcal{X}_k$`, wenn jeder PPT-Algorithmus nur mit höchstens vernachlässigbarer Wahrscheinlichkeit ein Urbild eines gegebenen, aus `$\mathcal{X}_k$` gezogenen Bildes findet. Für jeden PPT-Algorithmus `$\mathcal{A}$` ist `$Adv^{cr}_{H,\mathcal{A}}(k) := Pr[X' \leftarrow \mathcal{A}(1^k, H(X)): H(X) = H(X')]$` vernachlässigbar, wobei `$X \leftarrow \mathcal{X}_k$` gewählt wurde. </div> <div class="theorem"> Jede kollisionsresistente Hashfunktion `$H:\{0,1\}^* \rightarrow \{0,1\}^k$` ist eine Einwegfunktion bzgl. der Gleichverteilung auf `$\{0,1\}^{2k}$`. </div> <div class="theorem"> Ist `$f$` eine kollisionsresistente Hashfunktion, so ist die Merkle&ndash;Damg&aring;rd-Konstruktion mit `$f$` kollisionsresistent. </div> <div class="theorem"> Hash-Then-Sign-Paradigma: Sei (Sig, Ver) EUF-CMA-sicher und H eine kollisionsresistente Hashfunktion. Dann ist der durch Sig'(K, M) = Sig(K, H(M)), Ver'(K, M, `$\sigma$`) = Ver(K, H(M), `$\sigma$`) erklärte <abbr title="Message Authentification Code">MAC</abbr> EUF-CMA-sicher. </div> <h2>Fragen</h2> <div class="question"> <span class="question">Wann ist ein Verschlüsselungsschema IND-CPA-sicher?</span> <div class="answer"> IND-CPA bedeutet &bdquo;indistinguishability under chosen-plaintext attacks&ldquo;. Ein Verschlüsselungsschema ist genau dann IND-CPA-Sicher, wenn kein effizienter Angreifer `$\mathcal{A}$` Chiffrate von selbstgewählten Klartexten unterscheiden kann. </div> </div> <div class="question"> <span class="question">Wann ist eine Signatur EUF-CMA-sicher?</span> <div class="answer"> EUF-CMA bedeutet &bdquo;existentially unforgeable under chosen-message attacks&ldquo;. Eine Signatur ist genau dann EUF-CMA-Sicher, wenn alle PPT-Angreifer `$\mathcal{A}$` folgendes Spiel nur vernachlässigbar oft gewinnen: <ul> <li>`$\mathcal{A}$` hat Zugriff auf ein `$Sig(K, \cdot)$`-Orakel</li> <li>`$\mathcal{A}$` gibt als Ausgabe `$(M^*, \sigma^*)$`</li> <li>`$\mathcal{A}$` gewinnt, wenn `$Ver(K, M^*, \sigma^*) = 1$` und `$M^*$` &bdquo;frisch&ldquo; ist</li> </ul> </div> </div> <div class="question"> <span class="question">Was sind Replay-Angriffe?</span> <div class="answer"> Bei Replay-Angriffen fängt der Angreifer einen Teil der Kommunikation von Alice und Bob ab. Später schickt er diesen Teil ohne weitere Bearbeitung an einen der Beiden. </div> </div> <div class="question"> <span class="question">Was versteht man unter der Merkle&ndash;Damg&aring;rd-Konstruktion?</span> <div class="answer"> Die Merkle&ndash;Damg&aring;rd-Konstruktion ist eine Methode zur Konstruktion von kryptographischen Hash-Funktionen. Sie funktioniert so: <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/04/merkle-damgard-300x139.png"><img src="../images/2013/04/merkle-damgard-300x139.png" alt="Merkle-Damgard-Konstruktion" width="" height="" class="size-medium wp-image-74091" /></a><p class="wp-caption-text">Merkle-Damgard-Konstruktion<br />Quelle: <a href="http://commons.wikimedia.org/wiki/File:Merkle-Damgard_hash_big.svg">Wikipedia</a></p></div> </div> </div> <div class="question"> <span class="question">Wie funktioniert RSA?</span> <div class="answer"> <ol> <li>Generiere zwei Primzahlen `$p, q \in \mathbb{P}$`</li> <li>Berechne `$n := p \cdot q$` und `$\varphi(n) = (p-1) \cdot (q-1)$`</li> <li>Wähle `$e$`, sodass gilt: `$ggT(e, \varphi(n)) = 1$` und `$1 &lt; e &lt; \varphi(n)$`</li> <li>Berechne `$d$`, sodass gilt: `$e \cdot d \equiv 1 \mod \varphi(n)$`</li> </ol> Verschlüsselung einer Nachricht `$m$`: `$c = m^{e} \mod n$` Verschlüsselung eines Ciphertextes `$c$`: `$m = c^{d} \mod n$` </div> </div> <div class="question"> <span class="question">Welches Problem birgt ein kleines `$e$` beim RSA-Verfahren?</span> <div class="answer"> Folgender Angriff ist für `$e=3$` möglich: <ul> <li>Nachricht `$m$` wird an 3 Benutzer geschickt</li> <li>Angreifer kennt Chiffrate für `$N_1, N_2, N_3$`.</li> <li>Chinesischer Restsatz für `$m^3 \mod N_1 N_2 N_3$`.</li> <li>Wurzelziehen über `$\mathbb{Z}$` liefert `$m$`</li> </ul> </div> </div> <div class="question"> <span class="question">Was ist damit gemeint, wenn man sagt &bdquo;RSA ist Homomorph&ldquo;?</span> <div class="answer"> Homomorphie ist folgende (unerwünschte) Eigenschaft: `$\begin{align} Enc(pk, m_1) \cdot Enc(pk, m_2) &amp;= m_1^e \cdot m_2^e\\ &amp;= (m_1 \cdot m_2)^e \\ &amp;= Enc(pk, m_1 \cdot m_2) \end{align}$` Diese Eigenschaft ist z.B. in folgendem Szenario problematisch: Angenommen bei einer Auktion werden die gebotenen Geldbeträge verschlüsselt. Dann kann ein Angreifer das Chiffrat (gültig) verändern. So kann er den Geldbetrag ohne Probleme verdoppeln. </div> </div> <div class="question"> <span class="question">Was sind <abbr title="Hash-based message authentication code">HMACs</abbr>?</span> <div class="answer"> Spezielle symmetrische Signaturen, die wie folgt aufgebaut sind: `$Sig(K, M) = H(K \oplus opad, H(K \oplus ipad, M))$` </div> </div> <div class="question"> <span class="question">Wie funktioniert <a href="http://de.wikipedia.org/wiki/Elgamal-Verschl%C3%BCsselungsverfahren">ElGamal</a>?</span> <div class="answer"> <ol> <li>Wähle eine zyklische Gruppe `$\mathbb{G} = \langle g \rangle$`.</li> <li>`$pk = (\mathbb{G}, g, g^x)$`, `$sk=(\mathbb{G}, g, x)$`, wobei `$x$` zufällig gewählt wird.</li> </ol> Verschlüsselung einer Nachricht `$m$`: `$Enc(pk, m) = (g^y, g^{xy} \cdot m)$` mit zufälligem `$y$` &rarr; Verschlüsselung ist zufällig! Verschlüsselung eines Ciphertextes `$c$`: `$Dec(sk, (Y, Z)) = \frac{Z}{Y^x} = \frac{g^{xy} \cdot m}{(g^{y})^x} = m$` </div> </div> <div class="question"> <span class="question">Wie funktioniert das Kerberos-Schlüsselaustauschprotokoll?</span> <div class="answer"> <ul> <li>Alice schreibt dem <abbr title="Key Center">KC</abbr>, dass Alice und Bob gerne einen Schlüsselaustausch vornehmen wollen.</li> <li>Das KC schickt Alice ihren Schlüssel `$K_A$`, den sie für die Kommunikation mit Bob verwenden kann. Zusätzlich wird ein Zeitstempel `$T_{KC}$`, eine Gültigkeitsdauer `$L$` sowie ein frischer Schlüssel `$K$` übertragen.</li> <li>TODO!!!!</li> </ul> Ein <a href="http://www.youtube.com/watch?v=kp5d8Yv3-0c">gutes YouTube-Video</a> gibts auch. </div> </div> <div class="question"> <span class="question">Warum kann es schlecht für die Sicherheit sein, wenn man komprimiert?</span> <div class="answer"> Annahme: Ein Angreifer kann zu dem Geheimtext, der komprimiert wird, etwas vor der Kompression hinzufügen. Wenn der Ciphertext deutlich weniger wächst als er an Text hinzugefügt hat, kann er vermuten, dass er den Text erraten hat. (&rarr; CRIME-Angriff) </div> </div> <div class="question"> <span class="question">Was ist damit gemeint, dass das One-Time-Pad-Chiffre verwundbar ist?</span> <div class="answer"> Ein Angreifer kann die Klartextnachricht ändern. Wenn er wei&szlig; (oder zumindest ahnt) was der Klartext ist, kann er dafür sorgen, dass ein Klartext gleicher Länge seiner Wahl bei der Entschlüsselung herauskommt. </div> </div> <div class="question"> <span class="question">Nennen Sie Verfahren, die IND-CPA-sicher sind.</span> <div class="answer"> Eine Blockciffre im CBC-Modus </div> </div> <div class="question"> <span class="question">Nennen Sie Verfahren, die EUF-CMA-sicher sind.</span> <div class="answer"> Sei PRF: `$\{0,1\}^k \times \{0,1\}^k \rightarrow \{0,1\}^k$` eine PRF und `$H:\{0,1\}^* \rightarrow \{0,1\}^k$` eine kollisionsresistente Hashfunktion. Dann ist der durch `$Sig(K, M) = PRF(K, H(M))$` gegebene MAC EUF-CMA-sicher. </div> </div> <h2>Diverses</h2> <h3>TLS Handshake</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/04/tls-handshake.jpg"><img src="../images/2013/04/tls-handshake.jpg" alt="TLS Handshake" width="" height="" class="size-full wp-image-74511" /></a><p class="wp-caption-text">TLS Handshake</p></div> <h3>Change Cipher Spec Drop</h3> <p>Ein Angriff auf verschlüsselte Verbindungen:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/04/change-cipher-spec-drop.jpg"><img src="../images/2013/04/change-cipher-spec-drop.jpg" alt="Change cipher spec drop" width="" height="" class="size-full wp-image-74501" /></a><p class="wp-caption-text">Change cipher spec drop</p></div> <h2>Material</h2> <ul> <li><a href="http://www.iks.kit.edu/index.php?id=sic-sose13">Vorlesungswebsite</a></li> <li>Mein <a href="https://ankiweb.net/shared/info/4056558772">Anki-Deck</a></li> <li><a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_vorlaeufiges_Skript.pdf">Skript</a></li> <li>StackExchange: <ul> <li><a href="http://crypto.stackexchange.com/q/5646/7248">What are the differences between a digital signature, a MAC and a hash?</a></li> </ul> </li> </ul> <p>In der Fachschaft gibt es folgende Altklausuren:</p> <ol> <li>Hauptklausur SS 2012</li> <li>Nachklausur SS 2011</li> <li>Hauptklausur SS 2011</li> <li>Nachklausur SS 2010</li> <li>Hauptklausur SS 2010</li> </ol> <h2>Aufbau der Klausur</h2> <p>Bisher gab es meist 6 Aufgaben mit jeweils 10 Punkten:</p> <ol> <li>Blockchiffren und <a href="http://commons.wikimedia.org/wiki/User:MartinThoma#Betriebsmodi">Betriebsmodi</a></li> <li>ElGamal / <a href="http://de.wikipedia.org/wiki/Diffie-Hellman-Schl%C3%BCsselaustausch">Diffie-Hellman-Schlüsselaustausch</a></li> <li>RSA; RSA-OAEP</li> <li>Kerberos / Feistel / (H)MAC</li> <li>Bell-LaPadula / Chinese Wall</li> <li>Multiple Choice</li> </ol> <h2>Übungsbetrieb</h2> <p>Es gibt Übungsblätter auf der Vorlesungswebsite, aber keinen Übungsschein, keine Abgaben und keine Bonuspunkte.</p> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Freitag, den 26. Juli 2013 von 14:00 bis 15:00 Uhr (Klausur dauerte eine Stunde) <strong>Ort</strong>: seit 24.07.2013 auf der <a href="http://www.iks.kit.edu/sic-sose13">Vorlesungswebsite</a> (ich bin im H.S.a.F) <strong>Punkte</strong>: 60 <strong>Bestehensgrenze</strong>: 20 <strong>Übungsschein</strong>: Nein <strong>Bonuspunkte</strong>: Nein</p> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> <p>Sind noch nicht draußen (Stand: 30.07.2013)</p> <p>Sind nun draußen (Stand: 09.08.2013): <a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_HK-Ergebnis.pdf">Vorläufige Ergebnisse als PDF</a></p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/04/ergebnis-sicherheit-300x227.png"><img src="../images/2013/04/ergebnis-sicherheit-300x227.png" alt="Ergebnis der Sicherheitsklausur" width="" height="" class="size-medium wp-image-75851" /></a><p class="wp-caption-text">Ergebnis der Sicherheitsklausur</p></div> Semantische Sicherheit //martin-thoma.com/semantische-sicherheit/ Sun, 28 Apr 2013 15:06:53 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/semantische-sicherheit <p>In der <a href="http://www.iks.kit.edu/fileadmin/User/Lectures/Sicherheit/SoSe13/Sicherheit_VL03.pdf">Vorlesung vom 25.04.2013</a> hat Prof. Hofheinz gesagt, dass man semantische Sicherheit praktisch nicht beweisen kann, da man zuerst <span>\(\mathcal{P} \neq \mathcal{NP}\)</span> beweisen müsste. Warum das so ist, versuche ich nun zu erläutern.</p> <h2>Einwegfunktionen und <span>\(\mathcal{P} \neq \mathcal{NP}\)</span></h2> <div class="definition"> Sei <span>\(f:X \rightarrow Y\)</span> eine Funktion. <span>\(f\)</span> hei&szlig;t eine Einwegfunktion, genau dann wenn für alle <span>\(x \in X\)</span> gilt: <ul> <li><span>\(y := f(x)\)</span> kann in Polynomialzeit berechnet werden</li> <li>Für die Berechnung eines Urbildes <span>\(x\)</span> aus <span>\(y\)</span> existiert kein randomisierter Algorithmus, der in Polynomialzeit läuft.</li> </ul> </div> <p>Es gilt: Wenn eine Einwegfunktion <span>\(f\)</span> existiert, dann gilt <span>\(\mathcal{P} \neq \mathcal{NP}\)</span>.</p> <p>Warum?</p> <p>Nun, angenommen es gibt eine Einwegfunktion <span>\(f\)</span>. Dann sei die formale Sprache <span>\(L_f\)</span> definiert durch:</p> <p><span>\(L_f := \{(\bar x, y) | \exists x: \bar x \text{ ist Präfix von } x \text{ und } y = f(x)\}\)</span></p> <p>Es gilt: <span>\(L_f \notin \mathcal{P}\)</span>, da für ein gegebenes <span>\(y\)</span> das zugehörige <span>\(x\)</span> in polynomialzeit bestimmt werden könnte (wie will man sonst prüfen, ob <span>\(\bar x\)</span> ein Präfix von <span>\(x\)</span> ist?)</p> <p>Falls jemanden diese Begründung nicht ausreicht ist hier noch ein Beweis von Prof. Hofheinz (Danke!)</p> <p><strong>Beh.:</strong> <span>\(L_f \notin \mathcal{P}\)</span><br /> <strong>Bew.:</strong> durch Widerspruch<br /> <u>Annahme.:</u> <span>\(L_f \in P\)</span><br /> <span>\(\Rightarrow\)</span> Es existiert ein Polyzeit-Algorithmus <span>\(\mathcal{A}\)</span> für <span>\(L_f\)</span>, der bei Eingabe <span>\((\bar x, y)\)</span> entscheidet, ob ein <span>\(x\)</span> mit <span>\(f(x)=y\)</span> und Präfix <span>\(\bar x\)</span> existiert oder nicht. Dann können wir einen Algorithmus <span>\(\mathcal{B}\)</span> aus <span>\(\mathcal{A}\)</span> bauen, der <span>\(f\)</span> invertiert.</p> <p>Gegeben <span>\(y\)</span> verfährt <span>\(\mathcal{B}\)</span> wie folgt: <span>\(\mathcal{B}\)</span> ruft <span>\(\mathcal{A}(0,y)\)</span> auf und erfährt so, ob ein Urbild <span>\(x\)</span> von <span>\(y\)</span> mit Anfangsbit <span>\(0\)</span> existiert. Wenn ja, ruft <span>\(\mathcal{B}\)</span> den Algorithmus <span>\(\mathcal{A}(00,y)\)</span> auf, wenn nein ruft <span>\(\mathcal{B}\)</span> den Algorithmus <span>\(\mathcal{A}(10,y)\)</span> auf usw.</p> <p>So wird ein Urbild <span>\(x\)</span> bitweise bestimmt. Ein solches <span>\(\mathcal{B}\)</span> findet also effizient Urbilder, im Widerspruch zur Einwegannahme über <span>\(f \blacksquare\)</span></p> <p>Aber: Wenn das <span>\(x\)</span> gegeben ist, dann ist es einfach zu zeigen, dass <span>\(y= f(x)\)</span> gilt und damit auch, ob <span>\(\bar x\)</span> ein Präfix von <span>\(x\)</span> ist. Damit ist <span>\(L_f \in \mathcal{NP}\)</span>.</p> <p>Damit gilt: <span>\(L_f \in \mathcal{NP} \setminus \mathcal{P}\)</span>. Wenn aber <span>\(\mathcal{NP} \setminus \mathcal{P} \neq \emptyset\)</span>, dann gilt insbesondere <span>\(\mathcal{P} \neq \mathcal{NP}\)</span>.</p> <p>An dieser Stelle sollte man also einsehen, dass eine Einwegfunktion nach obiger Definition nur existieren kann, wenn <span>\(\mathcal{P} \neq \mathcal{NP}\)</span> gilt.</p> <h2>Semantische Sicherheit</h2> <p><a href="http://de.wikipedia.org/wiki/Sicherheitseigenschaften_kryptografischer_Verfahren#Semantische_Sicherheit">Wikipedia</a> gibt folgende Beschreibung von semantischer Sicherheit:</p> <blockquote>Ein Verschlüsselungsverfahren ist semantisch sicher, wenn jeder Angreifer jede Information, die er aus einem Chiffrat über die Nachricht ableiten kann, bereits dann ableiten kann, wenn er nur die Länge des Chiffrats kennt. Ein Chiffrat verrät also nichts über eine Nachricht als ihre Länge.</blockquote> <p>Herr Prof. Hofheinz hat folgende informelle Definition von Semantischer Sicherheit in der Vorlesung gegeben:</p> <div class="definition"> Ein symmetrisches Verschlüsselungsverfahren ist semantisch sicher, wenn es für jede <span>\(M\)</span>-Verteilung, jede Funktion <span>\(f\)</span> und jeden PPT-Algorithmus <span>\(\mathcal{A}\)</span> einen PPT-Algorithmus <span>\(\mathcal{B}\)</span> gibt, so dass <span>\(Pr \left [\mathcal{A}^{\text{Enc}(K, \cdot)}(\text{Enc}(K, M)) = f(M) \right ] - Pr [\mathcal{B}(\varepsilon) = f(M)]\)</span> vernachlässigbar (als Funktion im Sicherheitsparameter <span>\(K\)</span>) ist. </div> <p>Hier ist</p> <ul> <li><span>\(M\)</span> eine Nachricht (Message),</li> <li><span>\(\text{Enc(K, M)}\)</span> die Verschlüsselung einer konkreten Nachricht <span>\(M\)</span> mit dem Schlüssel <span>\(K\)</span>,</li> <li><span>\(\varepsilon\)</span> eine triviale Information (ich glaube das ist z.B. die Länge des Ciphertextes) und</li> <li><span>\(f\)</span> extrahiert beliebige Informationen aus dem Plaintext</li> </ul> <p>Die erste Wahrscheinlichkeit bezeichnet die Möglichkeit, aus dem Ciphertext Informationen der Art <span>\(f\)</span> über den Plaintext <span>\(M\)</span> zu erhalten. Die zweite Wahrscheinlichkeit bezeichnet die Möglichkeit „aus dem Nichts“ Informationen über eine Nachricht zu erhalten. Damit will man triviale Informationen eliminieren. Insgesamt gibt es also die Wahrscheinlichkeit an, nicht-triviale Informationen aus einer Verschlüsselten Nachricht zu erhalten. Mit effizient ist vermutlich in Polynomialzeit gemeint.</p> <p>Wenn es nun mehrfach benutzbare semantisch sichere Verfahren gibt, dann kann man dieses Verfahren als Einwegfunktion nutzen. Wenn eine Einwegfunktion existiert, gilt <span>\(\mathcal{P} \neq \mathcal{NP}\)</span>. Also folgt:</p> <p>Wenn es nun mehrfach benutzbare semantisch sichere Verfahren existieren, gilt <span>\(\mathcal{P} \neq \mathcal{NP}\)</span>. Dies ist aber eines der <a href="http://de.wikipedia.org/wiki/Millennium-Probleme">Millennium-Probleme</a> und noch nicht geklärt.</p> Google Code Jam – Round 1A 2013 //martin-thoma.com/google-code-jam-round-1a-2013/ Sat, 27 Apr 2013 07:15:17 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-round-1a-2013 <ul> <li>Problem A (<a href="https://code.google.com/codejam/contest/2418487/dashboard#s=p0">Bullseye</a>): <ul> <li>Small Set: 5856/6195 users (95%)</li> <li>Large Set: 1806/4795 users (38%)</li> </ul> <li>Problem B (<a href="https://code.google.com/codejam/contest/2418487/dashboard#s=p1">Manage your Energy</a>): <ul> <li>Small Set: 2323/3789 users (61%)</li> <li>Large Set: 456/1133 users (40%)</li> </ul> </li> <li>Problem C (<a href="https://code.google.com/codejam/contest/2418487/dashboard#s=p2">Good Luck</a>): <ul> <li>Small Set: 1366/1774 users (77%)</li> <li>Large Set: 31/605 users (5%)</li> </ul> </li> More information might soon be on <a href="http://www.go-hero.net/jam/13/">go-hero.net</a>. I'm too slow for Google Code Jam *sigh*. Nevertheless, here are my solutions: <h2>Bullseye</h2> <h3>Small</h3> ```php <? function solve($r, $t) { $circles = 0; while($t >= 0) { $circles++; $t -= ($r+1)*($r+1)-$r*$r; $r += 2; } return floor($circles) - 1; } $fp = fopen ($argv[1], 'r'); $testcases = fgets ($fp); $caseNr=0; while($line = fgets ($fp)) { $caseNr++; $a = explode(' ', $line); $r = $a[0]; $t = $a[1]; echo "Case #$caseNr: ".solve($r, $t)."\n"; } ?> ``` <h3>Large</h3> *Argh* I've copied the wrong equation from my pad to my computer You basically have to solve this: $`\begin{align} t - \sum_{i=0}^x ((r+1+2i)^2 - (r+2i)^2) &amp;\geq 0\\ \Leftrightarrow t - (x+1)(2x+2r+1) &amp;\geq 0 \\ \Leftrightarrow (-2)x^2 + (2r+3)x + (t-2r-1) &amp;\geq 0 \\ \Rightarrow x_{1,2} = 0 \Leftrightarrow x_{1,2} &amp;= \frac{1}{-4} \cdot (-(2r+3) \pm \sqrt{(2r+3)^2-4(-2)(t-2r-1)}) \\ &amp;= -\frac{1}{4} \cdot (-2r-3 \pm \sqrt{4r^2+12r+9+8(t-2r-1)})\\ &amp;= -\frac{1}{4} \cdot (-2r-3 \pm \sqrt{4r^2+12r+9+8t-16r-8})\\ &amp;= -\frac{1}{4} \cdot (-2r-3 \pm \sqrt{4r^2-4r+1+8t})\\ &amp;= \frac{1}{4} \cdot (2r+3 \pm \sqrt{(2r-1)^2+8t})\\ &amp;= \frac{1}{4} \cdot (2r+3 \pm \sqrt{(2r-1)^2+8t})\\ \end{align} `$ I have to know that $`1 \leq r`$ and $`1 \geq x \in \mathbb{N}`$. So you have to round $`x_1, x_2$ to the nearest solution. Did you know that Python has (in numpy) a method to calculate roots of a quadratic equation? See <a href="http://docs.scipy.org/doc/numpy/reference/generated/numpy.roots.html">numpy.roots</a> for reference. <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">ceil</span><span class="p">,</span> <span class="n">roots</span> <span class="k">def</span> <span class="nf">check</span><span class="p">(</span><span class="n">r</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">x</span><span class="p">):</span> <span class="k">return</span> <span class="n">t</span><span class="o">-</span><span class="p">(</span><span class="n">x</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">*</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">r</span><span class="o">+</span><span class="mi">2</span><span class="o">*</span><span class="n">x</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="o">&gt;=</span> <span class="mi">0</span> <span class="k">def</span> <span class="nf">solveFast</span><span class="p">(</span><span class="n">r</span><span class="p">,</span> <span class="n">t</span><span class="p">):</span> <span class="n">myRoots</span> <span class="o">=</span> <span class="n">roots</span><span class="p">((</span><span class="mi">2</span><span class="p">,</span><span class="mi">2</span><span class="o">*</span><span class="n">r</span><span class="o">+</span><span class="mi">3</span><span class="p">,</span><span class="mi">2</span><span class="o">*</span><span class="n">r</span><span class="o">+</span><span class="mi">1</span><span class="o">-</span><span class="n">t</span><span class="p">))</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">):</span> <span class="k">if</span> <span class="n">myRoots</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">&gt;=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">answer</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">ceil</span><span class="p">(</span><span class="n">myRoots</span><span class="p">[</span><span class="n">i</span><span class="p">]))</span> <span class="o">+</span> <span class="mi">1</span> <span class="k">while</span> <span class="ow">not</span> <span class="n">check</span><span class="p">(</span><span class="n">r</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">answer</span><span class="p">):</span> <span class="n">answer</span> <span class="o">-=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">answer</span> <span class="o">+</span> <span class="mi">1</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">line</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span> <span class="n">r</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solveFast</span><span class="p">(</span><span class="n">r</span><span class="p">,</span> <span class="n">t</span><span class="p">)))</span></code></pre></div> <h2>Good Luck</h2> This one solves at least the first test case, but not the second one. I love <a href="http://docs.python.org/2/library/itertools.html">itertools</a> ☺ <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">factorial</span> <span class="kn">from</span> <span class="nn">itertools</span> <span class="kn">import</span> <span class="n">combinations_with_replacement</span> <span class="kn">import</span> <span class="nn">pprint</span> <span class="kn">from</span> <span class="nn">copy</span> <span class="kn">import</span> <span class="n">deepcopy</span> <span class="k">def</span> <span class="nf">mul</span><span class="p">(</span><span class="n">integers</span><span class="p">):</span> <span class="n">s</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">p</span> <span class="ow">in</span> <span class="n">integers</span><span class="p">:</span> <span class="n">s</span> <span class="o">*=</span> <span class="n">p</span> <span class="k">return</span> <span class="n">s</span> <span class="k">def</span> <span class="nf">merge</span><span class="p">(</span><span class="n">candidates</span><span class="p">,</span> <span class="n">block</span><span class="p">):</span> <span class="n">newCandidates</span> <span class="o">=</span> <span class="n">deepcopy</span><span class="p">(</span><span class="n">candidates</span><span class="p">)</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="nb">set</span><span class="p">(</span><span class="n">block</span><span class="p">):</span> <span class="n">diff</span> <span class="o">=</span> <span class="n">block</span><span class="o">.</span><span class="n">count</span><span class="p">(</span><span class="n">el</span><span class="p">)</span> <span class="o">-</span> <span class="n">newCandidates</span><span class="o">.</span><span class="n">count</span><span class="p">(</span><span class="n">el</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">diff</span><span class="p">):</span> <span class="n">newCandidates</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">el</span><span class="p">)</span> <span class="k">return</span> <span class="n">newCandidates</span> <span class="k">def</span> <span class="nf">canBeIn</span><span class="p">(</span><span class="n">b</span><span class="p">,</span> <span class="n">candidates</span><span class="p">,</span> <span class="n">N</span><span class="p">):</span> <span class="n">merged</span> <span class="o">=</span> <span class="n">merge</span><span class="p">(</span><span class="n">candidates</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="k">return</span> <span class="ow">not</span> <span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">merged</span><span class="p">)</span> <span class="o">&gt;</span> <span class="n">N</span><span class="p">)</span> <span class="sd">&quot;&quot;&quot; </span> <span class="sd"> N: number of numbers in total that got randomly picked</span> <span class="sd"> M: A_i in [2, M]</span> <span class="sd">&quot;&quot;&quot;</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">N</span><span class="p">,</span> <span class="n">M</span><span class="p">,</span> <span class="n">products</span><span class="p">,</span> <span class="n">productToBuildungs</span><span class="p">):</span> <span class="n">candidates</span> <span class="o">=</span> <span class="p">[]</span> <span class="c"># Is there a simple answer?</span> <span class="k">for</span> <span class="n">p</span> <span class="ow">in</span> <span class="n">products</span><span class="p">:</span> <span class="k">if</span> <span class="n">productToBuildungs</span><span class="p">[</span><span class="n">p</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">candidates</span> <span class="o">=</span> <span class="n">merge</span><span class="p">(</span><span class="n">candidates</span><span class="p">,</span> <span class="n">productToBuildungs</span><span class="p">[</span><span class="n">p</span><span class="p">][</span><span class="mi">1</span><span class="p">][</span><span class="mi">0</span><span class="p">])</span> <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">candidates</span><span class="p">)</span> <span class="o">==</span> <span class="n">N</span><span class="p">:</span> <span class="k">return</span> <span class="n">candidates</span> <span class="k">for</span> <span class="n">p</span> <span class="ow">in</span> <span class="n">products</span><span class="p">:</span> <span class="n">pos</span> <span class="o">=</span> <span class="nb">filter</span><span class="p">(</span><span class="k">lambda</span> <span class="n">b</span><span class="p">:</span> <span class="n">canBeIn</span><span class="p">(</span><span class="n">b</span><span class="p">,</span> <span class="n">candidates</span><span class="p">,</span> <span class="n">N</span><span class="p">),</span> <span class="n">productToBuildungs</span><span class="p">[</span><span class="n">p</span><span class="p">][</span><span class="mi">1</span><span class="p">])</span> <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">pos</span><span class="p">)</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">candidates</span> <span class="o">=</span> <span class="n">merge</span><span class="p">(</span><span class="n">candidates</span><span class="p">,</span> <span class="n">pos</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="k">while</span> <span class="nb">len</span><span class="p">(</span><span class="n">candidates</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">N</span><span class="p">:</span> <span class="n">candidates</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="mi">2</span><span class="p">)</span> <span class="k">return</span> <span class="n">candidates</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">:&quot;</span> <span class="o">%</span> <span class="n">caseNr</span><span class="p">)</span> <span class="n">line</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span> <span class="n">arr</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">R</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">arr</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="n">N</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">arr</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span> <span class="n">M</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">arr</span><span class="p">[</span><span class="mi">2</span><span class="p">])</span> <span class="n">K</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">arr</span><span class="p">[</span><span class="mi">3</span><span class="p">])</span> <span class="c"># which products can I get</span> <span class="n">productToBuildungs</span> <span class="o">=</span> <span class="p">{}</span> <span class="k">for</span> <span class="n">r</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">N</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">product</span> <span class="ow">in</span> <span class="n">combinations_with_replacement</span><span class="p">(</span><span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span><span class="n">M</span><span class="o">+</span><span class="mi">1</span><span class="p">),</span><span class="n">r</span><span class="p">):</span> <span class="n">s</span> <span class="o">=</span> <span class="n">mul</span><span class="p">(</span><span class="n">product</span><span class="p">)</span> <span class="k">if</span> <span class="n">s</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">productToBuildungs</span><span class="p">:</span> <span class="n">productToBuildungs</span><span class="p">[</span><span class="n">s</span><span class="p">]</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="p">[</span><span class="nb">list</span><span class="p">(</span><span class="n">product</span><span class="p">)]]</span> <span class="k">else</span><span class="p">:</span> <span class="n">productToBuildungs</span><span class="p">[</span><span class="n">s</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">productToBuildungs</span><span class="p">[</span><span class="n">s</span><span class="p">][</span><span class="mi">1</span><span class="p">]</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">list</span><span class="p">(</span><span class="n">product</span><span class="p">))</span> <span class="k">for</span> <span class="n">r</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">R</span><span class="p">):</span> <span class="n">products</span> <span class="o">=</span> <span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="n">el</span><span class="p">)</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="k">if</span> <span class="nb">int</span><span class="p">(</span><span class="n">el</span><span class="p">)</span> <span class="o">!=</span> <span class="mi">1</span><span class="p">]</span> <span class="k">print</span><span class="p">(</span><span class="s">&#39;&#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span> <span class="nb">sorted</span><span class="p">(</span><span class="n">solve</span><span class="p">(</span><span class="n">N</span><span class="p">,</span> <span class="n">M</span><span class="p">,</span> <span class="n">products</span><span class="p">,</span> <span class="n">productToBuildungs</span><span class="p">)))))</span></code></pre></div> </li></ul> Google Code Jam Templates //martin-thoma.com/google-code-jam-templates/ Fri, 26 Apr 2013 11:17:35 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-templates <p>Here are some templates that are a good start for Google Code Jam.</p> <h2>C++</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">void</span><span class="p">)</span> <span class="p">{</span> <span class="cm">/* number of test cases */</span> <span class="kt">unsigned</span> <span class="kt">short</span> <span class="kt">int</span> <span class="n">testcases</span><span class="p">;</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">t</span><span class="p">;</span> <span class="k">for</span><span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">1</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="n">t</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="c1">//loops for each case</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">zeile</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">zeile</span><span class="o">&lt;</span><span class="mi">4</span><span class="p">;</span> <span class="n">zeile</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">spalte</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">spalte</span><span class="o">&lt;</span><span class="mi">4</span><span class="p">;</span> <span class="n">spalte</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">game</span><span class="p">[</span><span class="n">zeile</span><span class="p">][</span><span class="n">spalte</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Case #&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">i</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">solve</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Compile</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">g++ A.cpp</code></pre></div> <p>Execute</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">./a.out &lt; A-small-practice.in &gt; result.txt</code></pre></div> <h2>Python</h2> <ul> <li>Input: <a href="http://docs.python.org/2/library/functions.html#input">input</a>, <a href="http://docs.python.org/2/library/functions.html#raw_input">raw_input()</a></li> <li>String parsing: <a href="http://docs.python.org/2/library/stdtypes.html#str.strip">strip()</a>, <a href="http://docs.python.org/2/library/stdtypes.html#str.split">split()</a></li> </ul> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">testcases</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">cipher</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="p">,</span> <span class="n">solve</span><span class="p">(</span><span class="n">cipher</span><span class="p">)))</span></code></pre></div> <p>Execute</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python A.py &lt; A-small-practice.in &gt; result.txt</code></pre></div> <h2>Java</h2> <p>This is an ajusted version of mystics solution for “Dancing with Googlers”. You might want to take a look at <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Scanner.html">Scanner</a> and <a href="http://docs.oracle.com/javase/7/docs/api/java/io/PrintWriter.html">PrintWriter</a>.</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.*</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.*</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">DancingWithGoogle</span> <span class="o">{</span> <span class="kd">final</span> <span class="kd">static</span> <span class="n">String</span> <span class="n">PROBLEM_NAME</span> <span class="o">=</span> <span class="s">&quot;dance&quot;</span><span class="o">;</span> <span class="kd">final</span> <span class="kd">static</span> <span class="n">String</span> <span class="n">WORK_DIR</span> <span class="o">=</span> <span class="s">&quot;/home/moose/Desktop/&quot;</span> <span class="o">+</span> <span class="n">PROBLEM_NAME</span> <span class="o">+</span> <span class="s">&quot;/&quot;</span><span class="o">;</span> <span class="kd">final</span> <span class="kd">static</span> <span class="n">String</span> <span class="n">INPUT_FILE_NAME</span> <span class="o">=</span> <span class="s">&quot;input.txt&quot;</span><span class="o">;</span> <span class="kd">final</span> <span class="kd">static</span> <span class="n">String</span> <span class="n">OUTPUT_FILE_NAME</span> <span class="o">=</span> <span class="s">&quot;output.txt&quot;</span><span class="o">;</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">maxBest</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="mi">31</span><span class="o">][</span><span class="mi">2</span><span class="o">];</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">preprocess</span><span class="o">()</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="mi">30</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="n">Arrays</span><span class="o">.</span><span class="na">fill</span><span class="o">(</span><span class="n">maxBest</span><span class="o">[</span><span class="n">i</span><span class="o">],</span> <span class="o">-</span><span class="mi">1</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">A</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">A</span> <span class="o">&lt;=</span> <span class="mi">10</span><span class="o">;</span> <span class="n">A</span><span class="o">++)</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">B</span> <span class="o">=</span> <span class="n">A</span><span class="o">;</span> <span class="n">B</span> <span class="o">&lt;=</span> <span class="mi">10</span> <span class="o">&amp;&amp;</span> <span class="n">B</span> <span class="o">&lt;=</span> <span class="n">A</span> <span class="o">+</span> <span class="mi">2</span><span class="o">;</span> <span class="n">B</span><span class="o">++)</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">C</span> <span class="o">=</span> <span class="n">B</span><span class="o">;</span> <span class="n">C</span> <span class="o">&lt;=</span> <span class="mi">10</span> <span class="o">&amp;&amp;</span> <span class="n">C</span> <span class="o">&lt;=</span> <span class="n">A</span> <span class="o">+</span> <span class="mi">2</span><span class="o">;</span> <span class="n">C</span><span class="o">++)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">tot</span> <span class="o">=</span> <span class="n">A</span> <span class="o">+</span> <span class="n">B</span> <span class="o">+</span> <span class="n">C</span><span class="o">,</span> <span class="n">sur</span> <span class="o">=</span> <span class="o">(</span><span class="n">C</span> <span class="o">-</span> <span class="n">A</span> <span class="o">==</span> <span class="mi">2</span> <span class="o">?</span> <span class="mi">1</span> <span class="o">:</span> <span class="mi">0</span><span class="o">);</span> <span class="n">maxBest</span><span class="o">[</span><span class="n">tot</span><span class="o">][</span><span class="n">sur</span><span class="o">]</span> <span class="o">=</span> <span class="n">Math</span><span class="o">.</span><span class="na">max</span><span class="o">(</span><span class="n">maxBest</span><span class="o">[</span><span class="n">tot</span><span class="o">][</span><span class="n">sur</span><span class="o">],</span> <span class="n">C</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="kt">void</span> <span class="nf">solve</span><span class="o">(</span><span class="n">Scanner</span> <span class="n">sc</span><span class="o">,</span> <span class="n">PrintWriter</span> <span class="n">pw</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">N</span> <span class="o">=</span> <span class="n">sc</span><span class="o">.</span><span class="na">nextInt</span><span class="o">();</span> <span class="kt">int</span> <span class="n">S</span> <span class="o">=</span> <span class="n">sc</span><span class="o">.</span><span class="na">nextInt</span><span class="o">();</span> <span class="kt">int</span> <span class="n">p</span> <span class="o">=</span> <span class="n">sc</span><span class="o">.</span><span class="na">nextInt</span><span class="o">();</span> <span class="kt">int</span><span class="o">[]</span> <span class="n">tot</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">N</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">N</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="n">tot</span><span class="o">[</span><span class="n">i</span><span class="o">]</span> <span class="o">=</span> <span class="n">sc</span><span class="o">.</span><span class="na">nextInt</span><span class="o">();</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">dp</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">N</span> <span class="o">+</span> <span class="mi">1</span><span class="o">][</span><span class="n">N</span> <span class="o">+</span> <span class="mi">1</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="n">N</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="n">Arrays</span><span class="o">.</span><span class="na">fill</span><span class="o">(</span><span class="n">dp</span><span class="o">[</span><span class="n">i</span><span class="o">],</span> <span class="o">-</span><span class="mi">100000</span><span class="o">);</span> <span class="n">dp</span><span class="o">[</span><span class="mi">0</span><span class="o">][</span><span class="mi">0</span><span class="o">]</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">pos</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">pos</span> <span class="o">&lt;</span> <span class="n">N</span><span class="o">;</span> <span class="n">pos</span><span class="o">++)</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">sur</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">sur</span> <span class="o">&lt;=</span> <span class="n">pos</span><span class="o">;</span> <span class="n">sur</span><span class="o">++)</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">nSur</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">nSur</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="o">;</span> <span class="n">nSur</span><span class="o">++)</span> <span class="k">if</span> <span class="o">(</span><span class="n">maxBest</span><span class="o">[</span><span class="n">tot</span><span class="o">[</span><span class="n">pos</span><span class="o">]][</span><span class="n">nSur</span><span class="o">]</span> <span class="o">&gt;=</span> <span class="mi">0</span><span class="o">)</span> <span class="n">dp</span><span class="o">[</span><span class="n">pos</span> <span class="o">+</span> <span class="mi">1</span><span class="o">][</span><span class="n">sur</span> <span class="o">+</span> <span class="n">nSur</span><span class="o">]</span> <span class="o">=</span> <span class="n">Math</span><span class="o">.</span><span class="na">max</span><span class="o">(</span><span class="n">dp</span><span class="o">[</span><span class="n">pos</span> <span class="o">+</span> <span class="mi">1</span><span class="o">][</span><span class="n">sur</span> <span class="o">+</span> <span class="n">nSur</span><span class="o">],</span> <span class="n">dp</span><span class="o">[</span><span class="n">pos</span><span class="o">][</span><span class="n">sur</span><span class="o">]</span> <span class="o">+</span> <span class="o">(</span><span class="n">maxBest</span><span class="o">[</span><span class="n">tot</span><span class="o">[</span><span class="n">pos</span><span class="o">]][</span><span class="n">nSur</span><span class="o">]</span> <span class="o">&gt;=</span> <span class="n">p</span> <span class="o">?</span> <span class="mi">1</span> <span class="o">:</span> <span class="mi">0</span><span class="o">));</span> <span class="n">pw</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">dp</span><span class="o">[</span><span class="n">N</span><span class="o">][</span><span class="n">S</span><span class="o">]);</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="kd">throws</span> <span class="n">Exception</span> <span class="o">{</span> <span class="n">preprocess</span><span class="o">();</span> <span class="n">Scanner</span> <span class="n">sc</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Scanner</span><span class="o">(</span><span class="k">new</span> <span class="nf">FileReader</span><span class="o">(</span><span class="n">WORK_DIR</span> <span class="o">+</span> <span class="n">INPUT_FILE_NAME</span><span class="o">));</span> <span class="n">PrintWriter</span> <span class="n">pw</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">PrintWriter</span><span class="o">(</span><span class="k">new</span> <span class="nf">FileWriter</span><span class="o">(</span><span class="n">WORK_DIR</span> <span class="o">+</span> <span class="n">OUTPUT_FILE_NAME</span><span class="o">));</span> <span class="kt">int</span> <span class="n">caseCnt</span> <span class="o">=</span> <span class="n">sc</span><span class="o">.</span><span class="na">nextInt</span><span class="o">();</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">caseNum</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">caseNum</span> <span class="o">&lt;</span> <span class="n">caseCnt</span><span class="o">;</span> <span class="n">caseNum</span><span class="o">++)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Processing test case &quot;</span> <span class="o">+</span> <span class="o">(</span><span class="n">caseNum</span> <span class="o">+</span> <span class="mi">1</span><span class="o">));</span> <span class="n">pw</span><span class="o">.</span><span class="na">print</span><span class="o">(</span><span class="s">&quot;Case #&quot;</span> <span class="o">+</span> <span class="o">(</span><span class="n">caseNum</span> <span class="o">+</span> <span class="mi">1</span><span class="o">)</span> <span class="o">+</span> <span class="s">&quot;: &quot;</span><span class="o">);</span> <span class="k">new</span> <span class="nf">DancingWithGoogle</span><span class="o">().</span><span class="na">solve</span><span class="o">(</span><span class="n">sc</span><span class="o">,</span> <span class="n">pw</span><span class="o">);</span> <span class="o">}</span> <span class="n">pw</span><span class="o">.</span><span class="na">flush</span><span class="o">();</span> <span class="n">pw</span><span class="o">.</span><span class="na">close</span><span class="o">();</span> <span class="n">sc</span><span class="o">.</span><span class="na">close</span><span class="o">();</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Adjust the path and execute it within Eclipse.</p> <h2>PHP</h2> <p>Input / output:</p> <ul> <li>\`$fp = <a href="http://php.net/manual/en/function.fopen.php">fopen</a> (<a href="http://php.net/manual/en/reserved.variables.argv.php">$`argv[1]</a>, 'r'): Open file pointer to file in first command line argument</li> <li>string <a href="http://php.net/manual/en/function.fgets.php">fgets</a> (\$fp): Read one line</li> </ul> <p>Execute:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">php A.php input.txt &gt; output.txt</code></pre></div> <h2>JavaScript</h2> <p>Did you know that you can also solve those tasks with JavaScript? I’ve explained <a href="http://stackoverflow.com/a/16242806/562769">how to install v8</a>.</p> <p>Here is a <a href="http://www.go-hero.net/jam/13/name/aditsu">solution from aditsu</a>:</p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="c1">// run with v8: d8 file.js &lt; file.in</span> <span class="kd">var</span> <span class="nx">m</span><span class="p">,</span> <span class="nx">res</span><span class="p">,</span> <span class="nx">dot</span> <span class="kd">function</span> <span class="nx">check</span><span class="p">(</span><span class="nx">x0</span><span class="p">,</span> <span class="nx">y0</span><span class="p">,</span> <span class="nx">dx</span><span class="p">,</span> <span class="nx">dy</span><span class="p">)</span> <span class="p">{</span> <span class="kd">var</span> <span class="nx">x</span> <span class="o">=</span> <span class="mi">0</span> <span class="kd">var</span> <span class="nx">o</span> <span class="o">=</span> <span class="mi">0</span> <span class="kd">var</span> <span class="nx">t</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="p">(</span><span class="kd">var</span> <span class="nx">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="nx">i</span> <span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="o">++</span><span class="nx">i</span><span class="p">)</span> <span class="p">{</span> <span class="k">switch</span> <span class="p">(</span><span class="nx">m</span><span class="p">[</span><span class="nx">x0</span> <span class="o">+</span> <span class="nx">i</span> <span class="o">*</span> <span class="nx">dx</span><span class="p">][</span><span class="nx">y0</span> <span class="o">+</span> <span class="nx">i</span> <span class="o">*</span> <span class="nx">dy</span><span class="p">])</span> <span class="p">{</span> <span class="k">case</span> <span class="s1">&#39;X&#39;</span><span class="o">:</span><span class="nx">x</span><span class="o">++</span><span class="p">;</span><span class="k">break</span> <span class="k">case</span> <span class="s1">&#39;O&#39;</span><span class="o">:</span><span class="nx">o</span><span class="o">++</span><span class="p">;</span><span class="k">break</span> <span class="k">case</span> <span class="s1">&#39;T&#39;</span><span class="o">:</span><span class="nx">t</span><span class="o">++</span><span class="p">;</span><span class="k">break</span> <span class="k">case</span> <span class="s1">&#39;.&#39;</span><span class="o">:</span><span class="nx">dot</span><span class="o">=</span><span class="mi">1</span><span class="p">;</span><span class="k">break</span> <span class="p">}</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="nx">x</span> <span class="o">+</span> <span class="nx">t</span> <span class="o">==</span> <span class="mi">4</span><span class="p">)</span> <span class="nx">res</span> <span class="o">=</span> <span class="s1">&#39;X&#39;</span> <span class="k">if</span> <span class="p">(</span><span class="nx">o</span> <span class="o">+</span> <span class="nx">t</span> <span class="o">==</span> <span class="mi">4</span><span class="p">)</span> <span class="nx">res</span> <span class="o">=</span> <span class="s1">&#39;O&#39;</span> <span class="p">}</span> <span class="kd">var</span> <span class="nx">t</span> <span class="o">=</span> <span class="nx">readline</span><span class="p">()</span> <span class="k">for</span> <span class="p">(</span><span class="kd">var</span> <span class="nx">i</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="nx">i</span> <span class="o">&lt;=</span> <span class="nx">t</span><span class="p">;</span> <span class="o">++</span><span class="nx">i</span><span class="p">)</span> <span class="p">{</span> <span class="nx">m</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="p">(</span><span class="kd">var</span> <span class="nx">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="nx">j</span> <span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="o">++</span><span class="nx">j</span><span class="p">)</span> <span class="p">{</span> <span class="nx">m</span><span class="p">[</span><span class="nx">j</span><span class="p">]</span> <span class="o">=</span> <span class="nx">readline</span><span class="p">()</span> <span class="p">}</span> <span class="nx">readline</span><span class="p">()</span> <span class="nx">res</span> <span class="o">=</span> <span class="kc">null</span> <span class="nx">dot</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="p">(</span><span class="kd">var</span> <span class="nx">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="nx">j</span> <span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="o">++</span><span class="nx">j</span><span class="p">)</span> <span class="p">{</span> <span class="nx">check</span><span class="p">(</span><span class="nx">j</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">)</span> <span class="nx">check</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nx">j</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">)</span> <span class="p">}</span> <span class="nx">check</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">)</span> <span class="nx">check</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">)</span> <span class="nx">res</span> <span class="o">=</span> <span class="nx">res</span> <span class="o">?</span> <span class="nx">res</span> <span class="o">+</span> <span class="s1">&#39; won&#39;</span> <span class="o">:</span> <span class="nx">dot</span> <span class="o">?</span> <span class="s1">&#39;Game has not completed&#39;</span> <span class="o">:</span> <span class="s1">&#39;Draw&#39;</span> <span class="nx">print</span><span class="p">(</span><span class="s1">&#39;Case #&#39;</span> <span class="o">+</span> <span class="nx">i</span> <span class="o">+</span> <span class="s1">&#39;: &#39;</span> <span class="o">+</span> <span class="nx">res</span><span class="p">)</span> <span class="p">}</span></code></pre></div> Triangle area //martin-thoma.com/triangle-area/ Thu, 25 Apr 2013 10:13:15 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/triangle-area <p>I’ve just seen the following image on spikedmath.com:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/04/549-simple-area-quizz.png"><img src="../images/2013/04/549-simple-area-quizz.png" alt="Some geometry questions" width="" height="" class="size-full wp-image-64221" /></a><p class="wp-caption-text">Some geometry questions.<br />Source: <a href="http://spikedmath.com/549.html">spikedmath.com</a></p></div> <p>The second answers seem to be obviously the correct ones, right? Wrong.</p> <p>According to <a href="http://en.wikipedia.org/wiki/Heron%27s_formula">Heron’s formula</a> you can calculate a triangles area like this:</p> <p>Let <code>$a, b, c$</code> be the side lengths of the triangle. <code>$s := \frac{a+b+c}{2}$</code> <code>$T = \sqrt{s \cdot (s-a) \cdot (s-b) \cdot (s-c)}$</code></p> <p>So the area of the first triangle is <code>$s_1 := \frac{16}{2} = 8$</code> <code>$T_1 := \sqrt{8 \cdot (8-5) \cdot (8-5) \cdot (8-6)} = \sqrt{8 \cdot 3 \cdot 3 \cdot 2} = 3 \cdot 4 = 12$</code></p> <p>The area of the second one is <code>$s_1 := \frac{18}{2} = 9$</code> <code>$T_1 := \sqrt{9 \cdot (9-5) \cdot (9-5) \cdot (9-8)} = \sqrt{9 \cdot 4 \cdot 4 \cdot 1} = 3 \cdot 4 = 12$</code></p> <p>Both triangles have the same area!</p> <p>When you draw it, it looks like this:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/04/triangle-heron-tricky1.png"><img src="../images/2013/04/triangle-heron-tricky1.png" alt="Both triangles in one picture" width="" height="" class="size-full wp-image-64341" /></a><p class="wp-caption-text">Both triangles in one picture</p></div> Rechnernetze-Klausur //martin-thoma.com/rechnernetze-klausur/ Thu, 25 Apr 2013 09:32:06 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/rechnernetze-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesung &bdquo;Einführung in Rechnernetze&ldquo; des Moduls &bdquo;Kommunikation und Datenhaltung&ldquo; am KIT. Er dient als Prüfungsvorbereitung. Ich habe die Vorlesungen bei Herrn <a href="http://pcs.tm.kit.edu/21_beigl.php">Prof. Dr. Beigl</a> im Sommersemester 2013 gehört.</div> <h2>Behandelter Stoff</h2> <table> <tr> <td>16.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Einleitung</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Vorlesungsunterlagen/Folien/01_Einfuehrung_Rechnernetze.pdf">Kapitel 1</a></td> </tr> <tr> <td>24.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">E-Mail, <span class="hint" title="hochgradig gecachetes hirarchisches Datenbanksystem">DNS</span>, dig, nslookup, Peer-to-Peer-Netzwerke, Bootstrapping-Problem, ISO-/OSI-Schichtenmodell, <span class="hint" title="Service Access Points">SAPs</span>; Dienstgeber/-bringer, -funktionalität, -nehmer, -primitiv, -leistung; Request, Indication, Response, Confirm; <span class="hint" title="Quality of Service">QoS</span></td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Vorlesungsunterlagen/Folien/02_Architekturen_Rechnernetze.pdf">Kapitel 2</a>, Folie 18</td> </tr> <tr> <td>30.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;"><span class="hint" title="Service Data Unit">SDU</span>, <span class="hint" title="Protocoll Data Unit">PDU</span>, ISO / OSI-Architektur</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Vorlesungsunterlagen/Folien/02_Architekturen_Rechnernetze.pdf">Kapitel 2</a> bis wohin?</td> </tr> <tr> <td>21.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;"><a href="http://de.wikipedia.org/wiki/Zyklische_Redundanzpr%C3%BCfung">CRC</a>, Generatorpolynome, Vorwärtsfehlerkorrektur, Sequenznummern, Quittung, Stop-and-wait</td> </tr> <tr> <td style="border-bottom:1px solid black;">?</td> </tr> <tr> <td>28.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Protokollmechanismen und Verbindungen: Stop-and-wait; Go-Back-N <abbr title="Automatic Repeat Request">ARQ</abbr>, Flusskontrolle (Open Loop, Closed Loop); Kreditbasierte Flusskontrolle</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Vorlesungsunterlagen/Folien/04_Protokollmechanismen.pdf#page=36">Kapitel 4.5</a> - 4.8</td> </tr> <tr> <td>04.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">?</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Vorlesungsunterlagen/Folien/05_HDLC.pdf">Kapitel 5</a></td> </tr> <tr> <td>12.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Übungsblatt 2: <abbr title="Automatic Repeat Request">ARQ</abbr>: Bestätigter Dienst (JA), Zuverlässiger Dienst (JA, wenn...); Stop-and-Wait;</td> </tr> <tr> <td style="border-bottom:1px solid black;">?</td> </tr> <tr> <td>18.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Paketvermittlung</td> </tr> <tr> <td style="border-bottom:1px solid black;">7.2.2</td> </tr> <tr> <td>25.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Broadcast-Routing: Dateneinheit wird für jedes System erstellt; Hot-Potato; Potential des Missbrauchs (&rarr; <a href="https://www.youtube.com/watch?v=AOEQ9GteWbg">The Internet could crash. We need a Plan B.</a>); Outlaw-detection; Distanz-Vector-Routing; Link-State-Routing</td> </tr> <tr> <td style="border-bottom:1px solid black;">7-44</td> </tr> <tr> <td>02.07.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">IPv4 (Class A/B/C/D/E-Netze); <abbr title="Classless Inter-Domain Routing">CIDR</abbr>; Zuteilung von Adressen (<abbr title="Dynamic Host Configuration Protocol">DHCP</abbr>); Subnetze und Subnetz-Maskierung</td> </tr> <tr> <td style="border-bottom:1px solid black;">7-44</td> </tr> </table> <p>Falls hier was fehlt, könnt ihr mich gerne in den Kommentaren oder per Mail (info@martin-thoma.de) darauf aufmerksam machen. Ich bin ja mal gespannt, ob ich das bis zum Ende aktuell halte.</p> <h3>Übersicht über Dienstprimitive</h3> <table> <tr> <th>Name</th> <th>Dienstleistung</th> <th>Grundtypen</th> <th>Parameter</th> </tr> <tr> <td>Physical (Ph)</td> <td>Connect (Con)</td> <td>Request (Req)</td> <td colspan="7">Abhängig vom Dienst</td> </tr> <tr> <td>Data Link (DL)</td> <td>Data (Dat)</td> <td>Indication (Ind)</td> </tr> <tr> <td>Network (N)</td> <td>Release (Rel)</td> <td>Response (Rsp)</td> </tr> <tr> <td>Transport (T)</td> <td>Abort (Abo)</td> <td>Confirmation (Cnf)</td> </tr> <tr> <td>HTTP</td> <td>Provider Abort (PAbo)</td> <td>&nbsp;</td> </tr> <tr> <td>FTP</td> <td>Disconnect (Dis)</td> <td>&nbsp;</td> </tr> <tr> <td>...</td> <td>...</td> <td>&nbsp;</td> </tr> </table> <h2>Fragen</h2> <div class="question"> <span class="question">Welche Qualitätsparameter sind für Rechnernetze denkbar?</span> <div class="answer"> <ul> <li>Angemessenheit</li> <li>Technische Leistung (Antwortzeit, Datenrate)</li> <li>Zuverlässigkeit</li> <li>Sicherheit</li> <li>Kosten</li> </ul> </div> </div> <h2>Material</h2> <ul> <li><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Start/homepage.aspx">Vorlesungswebsite</a></li> <li><a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Lists/Forum/AllItems.aspx">Forum</a></li> <li><a href="https://ankiweb.net/shared/info/1739663871">Mein Anki-Deck</a></li> <li>Ein <a href="http://www.youtube.com/watch?v=0apqZ4jsGmI">Video über CRC</a></li> <li>Der Wikipedia-Artikel <a href="http://de.wikipedia.org/wiki/Routing">Routing</a> beinhaltet viele wichtige Informationen.</li> <li><a href="http://packetcrafter.wordpress.com/2011/02/13/tcp-flags-hackers-playground/">TCP flags: Hackers Playground</a></li> </ul> <h2>Aufbau der Klausur</h2> <p>Häufige Aufgabenstellungen sind:</p> <ul> <li>Berechnen einer Subnetzmaske bzw. ob eine IP-Adresse in einem gegebenem Subnetz enthalten ist</li> <li>CRC berechnen / überprüfen ob CRC korrekt ist</li> <li>Distanz-Vektor Algorithmus (Bellman-Ford) durchgehen</li> <li>Protokollablauf durchspielen</li> </ul> <h2>Übungsbetrieb</h2> <p>Übungsblätter sind <a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Vorlesungsunterlagen/Forms/AllItems.aspx?RootFolder=%2fsites%2fvab%2f0x2E18BE2A290A424EB98916CA7A6FF3FD%2fVorlesungsunterlagen%2fUebung&amp;FolderCTID=&amp;View=%7bF9CB46E3-13F6-4910-9A2E-BF24D999D119%7d">hier</a>.</p> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Donnerstag, den 1. August 2013 von 14:00 bis 15:00 Uhr<br /> <strong>Ort</strong>: Seit 28.07.2013 <a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Start/homepage.aspx">online</a>:<br /></p> <table> <tr> <th>Ort</th> <th>von</th> <th>bis</th> </tr> <tr> <td>Audimax A (30.95, EG)</td> <td>Abdullah</td> <td>Galler</td> </tr> <tr> <td>Audimax B (30.95, EG)</td> <td>Gassenschmidt</td> <td>Löffler</td> </tr> <tr> <td style="background-color:#cdcdcd">HSaF (50.35, EG)</td> <td>Loose</td> <td>Tobias</td> </tr> <tr> <td>Neue Chemie (30.46, EG)</td> <td>Traub</td> <td>Zumkeller</td> </tr> </table> <p><strong>Einsicht</strong>: 17.09.2013<br /> <strong>Punkte</strong>: 30<br /> <strong>Bestehensgrenze</strong>: 13 Punkte<br /> <strong>Notenskala</strong>:<br /></p> <table> <tr> <th>Note</th> <th>von</th> <th>bis</th> <th>Bereichsgrö&szlig;e</th> </tr> <tr> <th>1,0</th> <td>30,00</td> <td>26,50</td> <td>3,5</td> </tr> <tr> <th>1,3</th> <td>26,25</td> <td>25,00</td> <td>1,25</td> </tr> <tr> <th>1,7</th> <td>24,75</td> <td>23,50</td> <td>1,25</td> </tr> <tr> <th>2,0</th> <td>23,25</td> <td>22,00</td> <td>1,25</td> </tr> <tr> <th>2,3</th> <td>21,75</td> <td>20,50</td> <td>1,25</td> </tr> <tr> <th>2,7</th> <td>20,25</td> <td>19,00</td> <td>1,25</td> </tr> <tr> <th>3,0</th> <td>18,75</td> <td>17,50</td> <td>1,25</td> </tr> <tr> <th>3,3</th> <td>17,25</td> <td>16,00</td> <td>1,25</td> </tr> <tr> <th>3,7</th> <td>15,75</td> <td>14,50</td> <td>1,25</td> </tr> <tr> <th>4,0</th> <td>14,25</td> <td>13,00</td> <td>1,25</td> </tr> <tr> <th>5,0</th> <td>12,75</td> <td>00,00</td> <td>12,75</td> </tr> </table> <p><strong>Übungsschein</strong>: Nein<br /> <strong>Bonuspunkte</strong>: Nein</p> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> <p>Sind nun <a href="https://studium.kit.edu/sites/vab/0x2E18BE2A290A424EB98916CA7A6FF3FD/Lists/Ankuendigungen/DispForm.aspx?ID=11">online</a>. Hier ist die Statistik:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/04/klausur-rechnernetze-2013-300x274.png"><img src="../images/2013/04/klausur-rechnernetze-2013-300x274.png" alt="Klausurergebnisse Rechnernetze 2013" width="" height="" class="size-medium wp-image-76302" /></a><p class="wp-caption-text">Klausurergebnisse Rechnernetze 2013</p></div> E.i.d. Algebra und Zahlentheorie-Klausur //martin-thoma.com/eaz-klausur/ Tue, 23 Apr 2013 22:49:50 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/eaz-klausur <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesung &bdquo;Einf&uuml;hrung in die Algebra und Zahlentheorie&ldquo; (EAZ) am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei Herrn Prof. Dr. K&uuml;hnlein im Sommersemester 2013 geh&ouml;rt.</div> <h2>Behandelter Stoff</h2> <table> <tr> <td>16.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Teilbarkeit; ggT, kgV; Euklidischer Algorithmus</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=7">Kapitel 1.1</a></td> </tr> <tr> <td>17.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Primzahlen; Fundamentalsatz der Arithmetik; p-Adische Bewertung</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=11">Kapitel 1.2</a></td> </tr> <tr> <td>23.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Verteilung der Primzahlen; Sieb des Erasthostenes; Euler-Produkt; Dichtheitssatz</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=15">Kapitel 1.3</a></td> </tr> <tr> <td>24.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Magma, Monoid, Halbgruppe, Gruppe, Erzeugnis `$\langle X \rangle$`</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=15">Kapitel 2.2.1</a></td> </tr> <tr> <td>08.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Gruppenhomomorphismen</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=15">Kapitel 2.3.1 - 2.3.5</a></td> </tr> <tr> <td>15.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Faktorgruppen, Homomorphiesatz, Einfachheit, Freie Gruppen</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=40">Kapitel 2.4</a></td> </tr> <tr> <td>28.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Sylows&auml;tze; alternierende Gruppe `$A_n$`</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=51">Kapitel 2.6</a></td> </tr> <tr> <td>29.05.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Exkurs: Aufbau des Zahlensystems, Grothendieck-Konstruktion</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=56">Kapitel 2.7</a></td> </tr> <tr> <td>04.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Ringe, Ringhomomorphismen, Einheitengruppe, Nullteiler</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=61">Kapitel 3</a></td> </tr> <tr> <td>05.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Ideal; Chinesischer Restsatz</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/media/eazskript.pdf#page=65">Kapitel 3</a></td> </tr> </table> <h2>Material</h2> <ul> <li><a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/de">Vorlesungswebsite</a></li> <li><a href="https://ankiweb.net/shared/info/1756853157">Mein Anki-Deck</a> (digitale Karteikarten)</li> <li><a href="../mathematische-strukturen/" title="Mathematische Strukturen">&Uuml;berblick &uuml;ber mathematische Strukturen</a></li> <li>StackExchange <ul> <li>Das Urbild einer Gruppe unter einem Gruppenhomomorphismus ist eine Gruppe (<a href="http://math.stackexchange.com/q/476508/6876">Beweis</a>)</li> <li>Der Stabilisator einer Gruppenoperation ist eine Gruppe (<a href="../stabilizer-subgroup-subgroup/">Beweis</a>)</li> <li>Der Schnitt von Normalteilern ist wieder ein Normalteiler (<a href="../intersection-two-normal-subgroups-normal-subgroup/">Beweis</a>)</li> <li><a href="http://math.stackexchange.com/q/479039/6876">What does &ldquo;characteristic&rdquo; mean in mathematics?</a></li> <li>Wie man das Legendre-Symbol einfach berechnet: <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/Calculate-Legendre">Pseudocode</a></li> <li><a href="http://math.stackexchange.com/q/482158/6876">How many 3-Sylow groups are in a group of order 126?</a> - Durch die Frage (und die Kommentare) habe ich sehr viel gelernt!</li> <li><a href="http://math.stackexchange.com/q/483795/6876">How can I find decompositions in `$\mathbb{Z}[\sqrt{d}]$`?</a></li> <li><a href="http://math.stackexchange.com/q/473673/6876">Why is `$A_5$` a simple group?</a></li> <li><a href="http://math.stackexchange.com/q/476508/6876">Is the pre-image of a subgroup under a homomorphism a group?</a></li> </ul> </li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/eaz">Gedanken zu den Klausurhinweisen</a></li> <li>Eine sch&ouml;ne <a href="http://schickling.github.io/algorithms/">Skriptsammlung</a></li> </ul> <h2>Aufbau der Klausur</h2> <ul> <li>Eine Aufgabe, wo man das Legendre-Symbol ausrechnen muss</li> <li>Eine Aufgabe, wo man mit dem Satz von Lagrange wichtig ist</li> <li>Eine Aufgabe zu Normalteilern / Sylowgruppen</li> <li>Der Kleine Satz von Fermat / Homomorphiesatz</li> </ul> <h2>&Uuml;bungsbetrieb</h2> <ul> <li>Wo sind die &Uuml;bungsbl&auml;tter: <a href="http://www.math.kit.edu/iag3/lehre/einfalgzahl2013s/de">online</a></li> <li>Abgabeform: handschriftlich</li> <li>Abgabe: Donnerstags, K&auml;sten in Geb&auml;ude 1C</li> <li>R&uuml;cknahme: in den Tutorien</li> <li>Turnus: w&ouml;chentlich</li> <li>&Uuml;bungsschein verpflichtend: Nein</li> <li>Bonus durch &Uuml;bungsschein: Nein</li> </ul> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: 05.09.2013, 11:00 Uhr - 13:00 Uhr <strong>Zeit</strong>: 2 Stunden <strong>Ort</strong>: Hörsaal am Fasanengarten <strong>Punkte</strong>: 60 Punkte <strong>Bestehensgrenze</strong>: 22 Punkte <strong>Übungsschein</strong>: Gibt es (sogar benotet) <strong>Bonuspunkte</strong>: Nein</p> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> <p>Seit dem 12.09.2013 draußen:</p> <p>an den Informationstafeln bei den Räumen 4A-21.1 und 4B-01</p> Datenbanksysteme-Klausur //martin-thoma.com/datenbanksysteme-klausur/ Sat, 20 Apr 2013 13:35:01 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/datenbanksysteme-klausur <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesung &bdquo;Datenbanksysteme&ldquo; des Moduls &bdquo;Kommunikation und Datenhaltung&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei <a href="http://dbis.ipd.uni-karlsruhe.de/336.php">Herrn Prof. Dr. B&ouml;hm</a> im Sommersemester 2013 geh&ouml;rt.</div> <p>An diesem Artikel wird natürlich noch gearbeitet.</p> <h2 id="behandelter-stoff">Behandelter Stoff</h2> <table> <tr> <td>15.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;"><span class="hint" title="Sie lagern Komplexit&auml;t aus: Keine redundante Speicherung von Daten, verhindern Inkonsistenzen">Warum Datenbanken toll sind</span>; <span class="hint" title="Atomarit&auml;t und Isolation">Transaktionseigenschaften</span>; Datenschutz; Datensicherheit; Relationsmodell; Integrit&auml;tsbedingungen; Schl&uuml;ssel; Fremdschl&uuml;ssel; SQL; View; <span class="hint" title="Zeile ausw&auml;hlen">Selektion</span>; <span class="hint" title="Spalte ausw&auml;hlen">Projektion</span>; <span class="hint" title="Beliebige Kombination der Operationen Verbund, Vereinigung, Differenz, Durchschnitt, Umbennenung, Projektion, Selektion">Query-Algebra</span>; <span class="hint" title="Zwei Selektionen k&ouml;nnen deutlich unterschiedlich gro&szlig;e Ergebnismengen haben. Werden sie hintereinander ausgef&uuml;hrt, empfiehlt es sich die st&auml;rker einschr&auml;nkende Selektion zuerst auszuf&uuml;hren.">Anfrage-Optimierer</span>; <span class="hint" title="Der Anwender sagt nur welches Ergebnis er will, nicht wie es ermittelt werden soll.">Anfragen sind deklarativ</span>; 3-Ebenen-Architektur; Trennung zwischen Schema und Instanz, <a href="https://de.wikipedia.org/wiki/Online_Analytical_Processing#12_Regeln_nach_Codd">9 Codd'sche Regeln</a></td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1272879/Kap1-Einleitung.pdf">Kapitel 1</a></td> </tr> <tr> <td>18.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Datentyp, Instanz, Polymorphes Typsystem, Typkonstruktoren, ... (TODO)</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1274077/Kap2-Datenmodellierung.pdf">Kapitel 2</a> - <a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1274086/Kap3-DDL.pdf">Kapitel 3</a>, Folie 32</td> </tr> <tr> <td>22.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">SQL (alter, drop, index, unique); Index; ER-Diagramm; UML; Tr&auml;germenge `$\mu$`, Aktueller Zustand einer Variablen `$\sigma$`</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1274086/Kap3-DDL.pdf">Kapitel 3</a>, Folie 32 - <a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1274693/Kap4-ERModell.pdf">Kapitel 4</a>, Folie 33</td> </tr> <tr> <td>29.04.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Systemunabh&auml;ngige Modellierung - Strukturelle Seite; <span class="hint" title="keine Instanzen, aber Ableitungen">abstrakte Klassen</span>, <span class="hint" title="Enthalten Methoden zur Erzeugung von Klassen">Metaklassen</span>, Parametrisierte Klassen; <span class="hint" title="Auto: R&auml;der, Lenkrad, Motor, Karosserie, ...">Aggregation</span> und <span class="hint" title="Fu&szlig;ballmanschaft besteht aus Spielern">Assoziation</span></td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1275725/Kap5-DMfuerRealis.pdf">Kapitel 5</a>, Folie 1 - <a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1275734/Kap6-Abb-ER2RDM.pdf">Kapitel 6</a>, Folie 24</td> </tr> <tr> <td>06.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;"><abbr title="functional dependency">FD</abbr>, Reflexivit&auml;t, Projektivit&auml;t, Akkumulation, RAP-Regeln, Einf&uuml;geanomalie, L&ouml;schanomalie; Abh&auml;ngigkeitstreue / Verbundtreue; 1. - 4. Normalform</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1282295/Kap7-relEntwurf-Teil1.pdf">Kapitel 7</a></td> </tr> <tr> <td>13.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Nebenl&auml;ufigkeitsprobleme: Lost update, dirty read, non-repeatable read; Serielle Ausf&uuml;hrung beseitigt Probleme, aber IO/Kommunikation machts ineffizient; History, Prefix Commit-Closed, commited projection; Transaktionen</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1289715/Kap11-ConcurrencyControl.pdf">Kapitel 11</a></td> </tr> <tr> <td>24.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Serialisierbarkeitsgraph; Synthese-Verfahren; BCNF; Histories: <abbr title="Recoverability">RC</abbr>, <abbr title="Avoids Cascading Aborts: Lesen nur von commiteten Transaktionen">ACA</abbr>, <abbr title="Strict (einfach RC+ACA, oder?)">ST</abbr>; <span class="hint" title="Wenn ich eine Eigenschaft habe, dann gilt sie auch vor dem letzten commit">prefix commit-closed</span></td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1289715/Kap11-ConcurrencyControl.pdf">Kapitel 11</a></td> </tr> <tr> <td>27.06.2013</td> <td rowspan="2" style="border-bottom:1px solid black;">Kapitel 8: Relationale Algebra, Bereichskalk&uuml;l; Syntaktisch sicher `$\Rightarrow$` Semantisch sicher; Kapitel 12: Anwendungsprogrammierung</td> </tr> <tr> <td style="border-bottom:1px solid black;"><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1291006/Kap8-relAlg.pdf">Kapitel 8</a>, <a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1294925/Kap12-Schnittstellen.pdf">12</a></td> </tr> </table> <p>Falls hier was fehlt, könnt ihr mich gerne in den Kommentaren oder per Mail (info@martin-thoma.de) darauf aufmerksam machen. Ich bin ja mal gespannt, ob ich das bis zum Ende aktuell halte.</p> <h2 id="sql">SQL</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">create</span> <span style="color:#339;font-weight:bold">view</span> MG <span style="color:#080;font-weight:bold">as</span> <span style="color:#B06;font-weight:bold">select</span> Mitarbeiter, Gehalt <span style="color:#080;font-weight:bold">from</span> MGA <span style="color:#080;font-weight:bold">where</span> Gehalt &gt; <span style="color:#00D">70</span> </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">insert</span> <span style="color:#B06;font-weight:bold">into</span> MG <span style="color:#080;font-weight:bold">values</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Alice</span><span style="color:#710">'</span></span>, <span style="color:#00D">90</span>) </pre></div> </div> </div> <h2 id="fragen">Fragen</h2> <div class="question"> <span class="question">Was ist der Unterschied zwischen einem DBS und einem DBMS?</span> <div class="answer"> Ein <abbr title="Datenbankmanagementsystem">DBMS</abbr> ist eine Software zur Datenverwaltung. Die eigentlichen Daten sind in der Datenbank. Ein <abbr title="Datenbanksystem">DBS</abbr> ist eine DBMS und eine Datenbank. Ein DBMS kann mehrere Datenbanken verwalten. </div> </div> <div class="question"> <span class="question">Sei `$H = r_1[y] w_1[x] r_3[x] w_1[z] r_2[z] w_3[y] r_2[x] w_2[y] c1 r_3[y] c_3 w_2[z] c_2$`.<br />Welche Transaktionen sind in dieser History?</span> <div class="answer"> <ul> <li>Ein Eintrag `$r_i[x]$` bedeutet, dass die Transaktion `$i$` die Ressource `$x$` liest.</li> <li>Ein Eintrag `$w_i[x]$` bedeutet, dass die Transaktion `$i$` die Ressource `$x$` schreibt.</li> <li>`$c_i$` bedeutet, dass die `$i$`-te Transaktion commitet wird</li> </ul> Es gibt also die Transaktion `$T_1, T_2 \text{ und } T_3$` mit `$T_1 = r_1[y] w_1[x] c_1$` </div> </div> <h2 id="material">Material</h2> <ul> <li><a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/1272509?client_size=1366x655">Folien</a></li> <li><a href="http://dbis.ipd.uni-karlsruhe.de/1969.php">Vorlesungswebsite</a></li> <li><a href="https://ankiweb.net/shared/info/3786791111">Mein Anki-Deck</a> (digitale Karteikarten)</li> <li><a href="http://mitschriebwiki.nomeata.de/Datenhaltung.pdf.4.pdf">Mitschrieb-Wiki</a></li> </ul> <p>In der Fachschaft gibt es folgende Altklausuren:</p> <ul> <li>25. Februar 2011</li> <li>30. Juli 2010 (DB + Rechnernetze, mit L&ouml;sung)</li> </ul> <h2 id="aufbau-der-klausur">Aufbau der Klausur</h2> <p>Häufige Aufgabenstellungen sind:</p> <ul> <li>Histories und Transaktionen: Ist eine gegebene History RC, ACA, Strict?</li> <li>Modellierung</li> <li>SQL-Abfragen formulieren</li> </ul> <p>In der Klausur vom SS 2013 wurde das in 4 Aufgaben à 15 Punkte aufgeteilt. Unter anderem war diesmal der RAP-Algorithmus und der Dekompositionsalgorithmus relevant.</p> <h2 id="uumlbungsbetrieb">Übungsbetrieb</h2> <p>Es gibt nur ein “Übungsblatt” mit Bonuspunkten für die Klausur. Auf dieses beziehe ich mich.</p> <ul> <li>Wo sind die &Uuml;bungsbl&auml;tter: <a href="https://dalaran.ipd.kit.edu">Portal</a> - <a href="https://bscw.ira.uni-karlsruhe.de/pub/bscw.cgi/d1289127/SQL-%C3%9Cbungsblatt%20%28relevant%20f%C3%BCr%20Klausurbonus%29.pdf">Aufgaben</a></li> <li>Abgabeform: Online</li> <li>Abgabe: 07.07.2013</li> <li>R&uuml;cknahme: ?</li> <li>Turnus: Einmalig</li> <li>&Uuml;bungsschein verpflichtend: Nein</li> <li>Bonus durch &Uuml;bungsschein: Ja</li> </ul> <p>Ein paar interessante Informationen zum Blatt:</p> <div class="question"> <span class="question">Was ist mit "Brute-Force-Ans&auml;tze" in der Aufgabenstellung gemeint?</span> <div class="answer"> Antwort von Herrn Keller: Bei Anfragen, die nur eine Anzahl in der Projektionsliste erwarten, k&ouml;nnen sie mit einer Query <code>SELECT <korrekte_anzahl> FROM <irgendeiner_tabelle> das korrekte Ergebnistupel durch ausprobieren herausbekommen. Im Portal wird das zun&auml;chst als "korrekt" bewertet, allerdings werden wir das im Nachhinein filtern. <div class="question"> <span class="question">Wie kann man bei der ORACLE-Datenbank die Anzahl der ausgegebenen Zeilen beschr&auml;nken (LIMIT)?</span> <div class="answer"> <div class="highlight"><pre><code class="language-sql" data-lang="sql"><span class="k">SELECT</span> <span class="o">*</span> <span class="k">FROM</span> <span class="p">(</span> <span class="n">your</span> <span class="n">selection</span> <span class="p">)</span> <span class="k">WHERE</span> <span class="n">ROWNUM</span> <span class="o">&lt;=</span> <span class="mi">5</span></code></pre></div> </div> </div> Ein bisschen was zu <a href="http://en.wikipedia.org/wiki/Join_(SQL)">JOIN</a> sollte man sich durchlesen. Ich habe &uuml;brigens das folgende Captcha bekomme: <div style="width: 303px" class="wp-caption aligncenter"><a href="../images/2013/04/captcha-db.png"><img src="../images/2013/04/captcha-db.png" alt="Datenbanksysteme - Captcha" width="" height="" class="size-full wp-image-70581" /></a><p class="wp-caption-text">Datenbanksysteme - Captcha</p></div> Wie zur H&ouml;lle soll man das l&ouml;sen? Ich hatte auf &bdquo;448444&ldquo; getippt, aber das war falsch. ## Termine und Klausurablauf <strong>Datum</strong>: Mittwoch, den 31. Juli 2013 von 11:00 bis 13:00 Uhr <strong>Ort</strong>: seit 29.07.2013 online: <table> <tr> <th>Wer</th> <th>Wo</th> </tr> <tr> <td>Nachnamen A-G</td> <td>Gerthsen H&ouml;rsaal</td> </tr> <tr> <td>Nachnamen H-J</td> <td>Nusselt H&ouml;rsaal</td> </tr> <tr> <td>Nachnamen K-L</td> <td>H&ouml;rsaal Neue Chemie</td> </tr> <tr> <td>Nachnamen M-R</td> <td>Daimler H&ouml;rsaal</td> </tr> <tr> <td>Nachnamen S</td> <td>Gaede H&ouml;rsaal</td> </tr> <tr> <td>Nachnamen T-Z</td> <td style="background-color:#cdcdcd">Benz H&ouml;rsaal</td> </tr> </table> <strong>Punkte</strong>: 60 <strong>Bestehensgrenze</strong>: ? <strong>&Uuml;bungsschein</strong>: ? <strong>Bonuspunkte</strong>: ? ## Nicht vergessen <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> ## Ergebnisse Sind noch nicht drau&szlig;en (Stand: 20.04.2013) </irgendeiner_tabelle></korrekte_anzahl></code></div></div> KogSys-Klausur //martin-thoma.com/kogsys-klausur/ Fri, 19 Apr 2013 20:38:47 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/kogsys-klausur <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesung &bdquo;Kognitive Systeme&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei Herrn Dr. Waibel im Sommersemester 2013 geh&ouml;rt.</div> <h2>Behandelter Stoff</h2> <h3>Vorlesung</h3> <table> <tr> <td style="border-bottom:1px solid black;">15.04.2013</td> <td style="border-bottom:1px solid black;"><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/KogSysSkript.pdf#page=5">Kapitel 1</a></td> <td style="border-bottom:1px solid black;">Einf&uuml;hrung</td> </tr> <tr> <td style="border-bottom:1px solid black;">17.04.2013</td> <td style="border-bottom:1px solid black;">&nbsp;</td> <td style="border-bottom:1px solid black;">Faltung, Fouriertransformation, Dirac-Funktion</td> </tr> <tr> <td style="border-bottom:1px solid black;">29.04.2013</td> <td style="border-bottom:1px solid black;"><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/05_06-Classification_2013.pdf">Klassifikation I</a></td> <td style="border-bottom:1px solid black;">Schablonenanpassung: <span class="hint" title="Skalierung, Perspektiven, Drehung, Verzerrung, Helligkeit">Probleme</span>, Statistische Auswertung immer wichtig da Signale ambig sind, Assoziative Netze, Bayes Decision Theorie, Gaussian Classificator - "Covarianzmatrix tut das Richtige [und eliminiert von einander Abh&auml;ngige Dimensionen]", Mahalanobis-Distanz; Gauss-Klassifikator ist quadratischer Form (Kreis, Ellipse, Linie), Overfitting = "Vorurteil" passiert, wenn man zu wenig Daten bzw. zu viele Dimensionen daf&uuml;r hat - "Fluch der Dimensionalit&auml;t"; Hauptachsentransformation reduziert Dimensionalit&auml;t</td> </tr> <tr> <td style="border-bottom:1px solid black;">06.05.2013</td> <td style="border-bottom:1px solid black;"><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/07_08-MachineLearning_2013.pdf">Machine Lerning</a></td> <td style="border-bottom:1px solid black;">Klassifikation: Risikobetrachtung bei Klassifikatoren, Gaussian Mixtures, Parzan Windows (nicht-parametrisiert, &uuml;berwacht), Fisher Linear Discriminant (scatter matrix), Linear seperable, <a href="https://en.wikipedia.org/wiki/K-nearest_neighbors_algorithm">K-nearest neighbors</a> (nicht-parametrisch, nicht-linear, &uuml;berwacht)</td> </tr> <tr> <td style="border-bottom:1px solid black;">13.05.2013</td> <td style="border-bottom:1px solid black;"><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/07_08-MachineLearning_2013.pdf#page=25">Neural Nets</a></td> <td style="border-bottom:1px solid black;">Perceptron Criterion Function; <abbr title="Multilevel Perceptron">MLP</abbr></td> </tr> <tr> <td style="border-bottom:1px solid black;">27.05.2013</td> <td style="border-bottom:1px solid black;"><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/09_Bildverarbeitung1-2013.pdf">Bildverarbeitung I</a></td> <td style="border-bottom:1px solid black;">Lochkartenmodell, HSI-Farbmodell, RGB2HSI, RGB2Graustufen, <a href="http://de.wikipedia.org/wiki/Punktoperator_(Bildverarbeitung)#Histogrammspreizung_und_-stauchung">Histogrammspreizung</a></td> </tr> <tr> <td style="border-bottom:1px solid black;">29.05.2013</td> <td style="border-bottom:1px solid black;"><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/10_Bildverarbeitung2-2013.pdf">Bildverarbeitung II</a></td> <td style="border-bottom:1px solid black;">Pixel-Transformation, Bildverarbeitung, Merkmalsextraktion, Form, Struktur, Klassifikation</td> <tr> <td style="border-bottom:1px solid black;">03.06.2013</td> <td style="border-bottom:1px solid black;">(Nicht verf&uuml;gbar)</td> <td style="border-bottom:1px solid black;">2D-Bildverarbeitung: Schwellwert, Graustufen, Segmentierung, Kanten-/Knotenerkennung; Hough-Tranformation; Harris-Corner-Detector; Kalmanfilter; Erosion / Dilatation; &Ouml;ffnen / Schlie&szlig;en</td> <tr> <td style="border-bottom:1px solid black;">10.06.2013</td> <td style="border-bottom:1px solid black;">(Nicht verf&uuml;gbar)</td> <td style="border-bottom:1px solid black;">Spracherkennung: Lautbildung, Vokale werden durch 1., 2. Formante bestimmt</td> </tr> <tr> <td style="border-bottom:1px solid black;">24.06.2013</td> <td style="border-bottom:1px solid black;">(Nicht verf&uuml;gbar)</td> <td style="border-bottom:1px solid black;">3D-Bildverarbeitung: Kalmanfilter; Partikelfilter; homogene Koordinaten</td> </tr> Falls hier was fehlt, k&ouml;nnt ihr mich gerne in den Kommentaren oder per Mail (info@martin-thoma.de) darauf aufmerksam machen. <h3>Folien</h3> <h4>01: Einf&uuml;hrung</h4> Nichts interessantes. <h4>02, 03: Digital Signal Processing</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Alias-Effekt">Alias-Effekt</a>, <a href="http://de.wikipedia.org/wiki/Nyquist-Shannon-Abtasttheorem">Abtasttheorem</a></li> <li>Digitalisierung: Zeit- und Wertdiskretisierung</li> <li><a href="http://de.wikipedia.org/wiki/Dirac-Funktion">Dirac-Funktion</a></li> <li>Faltung</li> <li>Fouriertransformation</li> <li>Korrelation: Autokorrelation, Kreuzkorrelation</li> </ul> <h4>04: Intelligente und Kognitive Systeme</h4> Interessant, aber vermutlich nicht Klausurrelevant. <h4>05, 06: Klassifikation</h4> <ul> <li>Schablonenanpassung: Wie &auml;hnlich ist das Muster einer Schablone?</li> <li>Normalisierung der Helligkeit</li> <li>Gauss-Klassifikation: Parametrisch</li> <li>Parzen Window: Nicht parametrisch</li> <li>k-nearest-neighbor: nicht parametrisch</li> <li>Perceptron: nicht parametrisch</li> <li>Bayes-Regel</li> <li>Principal Component Analysis (PCA)</li> <li>Linear Discriminant Function, Fisher-Linear Discriminant</li> </ul> <h4>07, 08: Machine Learning</h4> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/04/pattern-recognition-classification-300x172.png"><img src="../images/2013/04/pattern-recognition-classification-300x172.png" alt="Pattern recognition classification" width="" height="" class="size-medium wp-image-76312" /></a><p class="wp-caption-text">Pattern recognition classification<br />Image Source: Folien von Prof. Waibel</p></div> <ul> <li>Perceptron&lt;: <a href="http://de.wikipedia.org/wiki/Sigmoidfunktion">Sigmoidfunktion</a>/li&gt; <li>Classifier Discriminant Functions</li> <li>Linear Discriminant Functions</li> <h4>09: Bildverarbeitung I</h4> <ul> <li>Bildrepr&auml;sentation als Monochrombild</li> <li>RGB / HSI-Modell</li> <li>Bayer-Pattern</li> <li>Lochkamera-Modell</li> <li>Affine Punktoperatoren: `$g := round(a \cdot I(u,v) + b) I'(u,v) := \begin{cases} 0 &amp;\text{, falls } g &lt; 0\\ q &amp;\text{, falls } g &gt; q\\ g &amp;\text{sonst} \end{cases}$` <ul> <li>Kontrasterh&ouml;hung: `$b=0; a &gt; 1$`</li> <li>Kontrastverminderung: `$b=0; a &lt; 1$`</li> <li>Helligkeitserh&ouml;hung: `$b&gt;0; a = 1$`</li> <li>Helligkeitsverminderung: `$b&lt;0; a = 1$`</li> <li>Invertierung: `$b=q; a =-1$`</li> </ul> </li> <li>Nicht-Affine Punktoperatoren</li> <li>Automatische Kontrastanpassung (Spreizung, Histogrammdehnung, Histogrammausgleich)</li> </ul> <h4>10: Bildverarbeitung II</h4> <ul> <li>Fourier-Transformation</li> <li>2D Fourier-Transformation</li> <li>Fourier-R&uuml;cktransformation</li> <li>Ortsbereich / Frequenzbereich</li> <li>Tiefpassfilter <ul> <li>Mittelwertfilter: Rauschunterdr&uuml;ckung</li> <li><strong>Gau&szlig;-Filter</strong>: Rauschunterdr&uuml;ckung, Gl&auml;ttung</li> </ul> </li> <li>Hochpassfilter <ul> <li>Prewitt</li> <li>Sobel</li> <li>Laplace</li> <li>Roberts</li> </ul> </li> <li>KOmbinierte Operatoren <ul> <li>Laplacian of Gaussian</li> </ul> </li> <li>Canny-Kantendetektor</li> </ul> <h4>11: Bildverarbeitung III</h4> <ul> <li>Segmentierung (Schwelltwert, Farbe)</li> <li>Morphologische Operatoren: Dilatation, Erosion</li> <li>&Ouml;ffnen, Schlie&szlig;en</li> <li>Hough-Transformation</li> <li>Sum of Squared Differences; Zero Mean Normalized Cross-Correlation</li> <li>Partikelfilter</li> </ul> <h4>12: Spracherkennung</h4> <ul> <li>Faltung</li> <li>Formanten</li> <li>Spektogramm</li> <li>Akustisches Modell, Sprachmodell</li> <li>(Hidden-)Markov-Modell</li> <li><strong>Forward-, Forward-Backward- und Viterbi-Algorithmus</strong></li> </ul> <h4>13: ?</h4> <h4>14: ?</h4> <h4>15: Bildverarbeitung IV</h4> <ul> <li>Geometrische 3D-Transformationen: Rotation um Achsen</li> <li>Quaternionen</li> <li>Erweitertes Lochkameramodell</li> <li>Kamerakalibrierung</li> <li>Diskrete Lineare Transformation</li> <li>Stereorekonstruktion</li> <li>Epipolargeometrie</li> <li>Fundamentalmatrix</li> </ul> <h4>16: Visuelle Wahrnehmung</h4> Vermutlich nichts Klausurrelevantes (offiziell ab Folie 25) <h4>17: Wissen und Planung I</h4> <ul> <li>Satz, Wissensdatenbank, Deduktion</li> <li>Symbolmenge, Modellmenge, Syntax, Semantik</li> <li>Korrektheit und vollst&auml;ndigkeit eines Deduktions-Algorithmus</li> <li>Algorithmen: <strong>Resolution, Horn-Klauseln, DPLL</strong></li> <li>Planungssprachen: <strong><abbr title="STanford Research Institute Problem Solver">STRIPS</abbr>, <abbr title="Action Description Language">ADL</abbr></strong></li> <li><strong>A*-Suche, Partial-Order-Planning, Planungsgraphen</strong></li> </ul> <h4>18: Wissen und Planung II</h4> <ul> <li>Partial-Order-Planning</li> <li>Planungsgraphen</li> <li>Kantenmodell, Oberfl&auml;chenmodell, Volumenmodell</li> <li>Freiraum, Hindernisraum, Konfigurationsraum</li> <li>Polygonzerlegung</li> <li>Sichtgraphen</li> <li>Quadtrees</li> <li>Voronoi-Diagramme</li> <li>Potentialfeldmethode</li> </ul> <h4>19: Robotik</h4> Offiziell nicht Klausurrelevant. <h2>Material</h2> <ul> <li><a href="http://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/">Vorlesungswebsite</a></li> <li><a href="https://ankiweb.net/shared/info/2853080322">Mein Anki-Deck</a></li> <li><a href="http://www.next-internet.com/hauptstudium/">Klausuren</a></li> <li><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/vorlesungsfolien.php">Folien</a></li> <li><a href="https://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/save/KogSysSkript.pdf">Skript</a></li> <li><a href="https://github.com/elm/KogSys-Zusammenfassung">Zusammenfassung</a></li> <li>Videos <ul> <li><a href="http://www.youtube.com/watch?v=aVId8KMsdUU">Neural network tutorial: The back-propagation algorithm</a></li> <li><a href="http://www.youtube.com/watch?v=46Jzu-xWIBk">The backpropagation algorithm</a></li> </ul> </li> <li>Pseudocode f&uuml;r <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/DPLL">DPLL-Verfahren</a></li> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/Resolutionsalgorithmus">Resolutions-Algorithmus</a></li> </ul> </li> <li><a href="http://colorizer.org/">Colorizer</a>: Hier kann man ein bisschen mit Farbr&auml;umen rumspielen und die Unterschiede interaktiv feststellen.</li> <li>StackOverflow: <ul> <li><a href="http://math.stackexchange.com/q/487245/6876">Why is `$(-1) \cdot j = j \cdot (-1)$` for quaternions?</a></li> </ul> </li> <li>Artikel: <ul> <li><a href="../graphic-filters/">Graphic filters</a>: Mit einem interaktiven Beispiel aller Filter!</li> <li><a href="../k-nearest-neighbor-clustering-interactive-example/">Clustering-Algorithmen</a>: Mit interaktivem Beispiel</li> <li><a href="../calculations-with-quaternions/">Calculations with quaternions</a></li> <li><a href="../calculate-histogram-equalization/">How do I calculate a histogram equalization?</a></li> <li><a href="../apply-viterbi-algorithm/">How to apply the Viterbi algorithm</a></li> <li><a href="../html5/route-planning/route-planning.htm">Interactive example for route planning</a></li> <li><a href="../word-error-rate-calculation/">Word Error Rate (WER) calculation</a></li> </ul> </li> <li>Grafische Faltung: <ul> <li><a href="http://www.jhu.edu/signals/convolve/">John Hopkins University</a>, Java Applet</li> <li><a href="http://www.onmyphd.com/?p=convolution">onmyphd.com</a>, JavaScript</li> </ul> </li> </ul> Das Passwort f&uuml;r kogsys darf ich auch im Jahr 2013 nicht verraten. <h2>Aufbau der Klausur</h2> 6 Aufgaben: <ul> <li>Bildverarbeitung</li> <li>Bildverarbeitung, Filter und Transformation</li> <li>Logik, Wissensrepr&auml;sentation und Planung <ul> <li>Eine Aufgabe, in der man den Resolutionsalgorithmus / das DPLL-Verfahren anwenden muss</li> <li>A*-Algorithmus</li> </ul> </li> <li>Allgemeine Fragen</li> <li>Signal- und Sprachverarbeitung</li> <li>Klassifikation und Maschinelles Lernen</li> </ul> <h2>&Uuml;bungsbetrieb</h2> <ul> <li>Wo sind die &Uuml;bungsbl&auml;tter: <a href="http://his.anthropomatik.kit.edu/Teaching/VorlesungKognitiveSysteme/websubmit/student/blattuebersicht.php">Link</a></li> <li>Abgabeform: nur Handschriftlich</li> <li>Abgabe: teilweise online, teilweise offline, wenn offline m&uuml;ssen die &Uuml;bungsbl&auml;tter direkt vor der &Uuml;bung abgegeben werden, oder irgendwann davor im B&uuml;ro des &Uuml;bungsleiters in der Kinderklinik. Direkt im B&uuml;ro scheint ihm aber nicht so lieb zu sein.</li> <li>R&uuml;cknahme: gar nicht, empfohlen wird eine Kopie des Originals zu behalten</li> <li>Turnus: ? (6 Bl&auml;tter insgesammt)</li> <li>&Uuml;bungsschein verpflichtend: es gibt keinen &Uuml;bungsschein soweit ich wei&szlig;</li> <li>Bonus durch &Uuml;bungsschein: pro &Uuml;bungsblatt max. 1 Bonuspunkt &rarr; max. 6 Bonuspunkte (es gibt tats&auml;chlich 0,25-Punkte!)</li> </ul> <h2>Termine und Klausurablauf</h2> <strong>Datum</strong>: Mittwoch, den 18. September 2013 von 11:00 bis 12:00 Uhr<br /> <strong>Ort</strong>: steht noch nicht fest (Stand: 12.09.2013)<br /> <strong>Punkte</strong>: 60<br /> <strong>Bestehensgrenze</strong>: 20<br /> <strong>&Uuml;bungsschein</strong>: Gibt es nicht<br /> <strong>Bonuspunkte</strong>: Ja, max 6<br /> <strong>Ergebnisse</strong>: ab 14.10.2013 im Websubmit und in 50.20. (Kinderklinik) am Eingang<br /> <strong>Einsicht</strong>: 24.10.2013 von 13:30 bis 14:30 Uhr (Kinderklinik, Raum 148)<br /> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> Sind noch nicht drau&szlig;en (Stand: 18.09.2013) </li></ul></tr></tr></table> Numerik-Klausur //martin-thoma.com/numerik-klausur/ Fri, 19 Apr 2013 20:05:19 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/numerik-klausur <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesung &bdquo;Numerische Mathematik f&uuml;r die Fachrichtungen Informatik und Ingenieurwesen&ldquo; des Moduls &bdquo;Praktische Mathematik&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei Herrn Dr. Wei&szlig; im Sommersemester 2013 geh&ouml;rt.</div> <h2>Behandelter Stoff</h2> <p><strong>Vorlesung</strong>:</p> <table> <tr> <td>17.04.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel1.pdf">Kapitel 1.1</a></td> <td>Wiederholung LGS, <a href="../solving-linear-equations-with-gaussian-elimination/" title="Solving linear equations with Gaussian elimination">Gausches Eliminationsverfahren</a>, <a href="http://www.youtube.com/watch?v=MTKkiSCBo74">LR-Zerlegung</a>, Frobeniusmatrix</td> </tr> <tr> <td>24.04.2013</td> <td>&nbsp;</td> <td>&nbsp;</td> </tr> <tr> <td>01.05.2013</td> <td>&nbsp;</td> <td>&nbsp;</td> </tr> <tr> <td>08.05.2013</td> <td>&nbsp;</td> <td>&nbsp;</td> </tr> <tr> <td>15.05.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel1.pdf#page=19">Kapitel 1.4</a></td> <td>Vorw&auml;rts- und R&uuml;ckw&auml;rtsanalyse</td> </tr> <tr> <td>22.05.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel1.pdf#page=29">Kapitel 1.7</a></td> <td>Lineare Ausgleichsprobleme; QR-Zerlegung</td> </tr> <tr> <td>29.05.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel1.pdf#page=29">Kapitel 1.7</a>-2.1</td> <td>Fixpunktiteration</td> </tr> <tr> <td>05.06.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel2.pdf#page=4">Kapitel 2</a></td> <td>Banachscher Fixpunktsatz; Newton-Verfahren; Vereinfachtes Newton-Verfahren</td> </tr> <tr> <td>12.06.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel3a.pdf">Kapitel 3</a> - 3.1.2</td> <td>Interpolation von Funktionen mittels Polynomen (&rarr; <a href="../polynomial-interpolation/" title="Polynomial interpolation">Artikel</a>); Monomdarstellung; Lagrange-Polynome; Newton-Polynome; Dividierende Differenzen</td> </tr> <tr> <td>26.06.2013</td> <td><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/media/kapitel3.pdf#page=15">Kapitel 3.2</a> - S. 54, unten</td> <td><a href="../spline-interpolation/" title="Spline interpolation">Kubische Spline-Interpolation</a> &rarr; <a href="../html5/polynom-interpolation.htm">Visualisierung</a></td> </tr> </table> <h3>Skript</h3> <p>Kapitel 1:</p> <ul> <li>Wann ist ein LGS eindeutig l&ouml;sbar? Wann gibt es unendlich viele L&ouml;sungen?</li> <li>Gau&szlig;sches Eliminationsverfahren</li> <li>Was versteht man unter Vorw&auml;rts / R&uuml;ckw&auml;rtssubstitution?</li> <li>Beim Gau&szlig;'schen Eliminationsverfahren mit Spaltenpivotwahl tauscht man eine Zeile nach oben. Ist es das betragsm&auml;&szlig;ig gr&ouml;&szlig;te oder kleinste? Warum?</li> <li>Was ist eine Permutationsmatrix? Was eine Frobeniusmatrix?</li> <li>LR-Zerlegung</li> <li>Was ist eine unipotente Dreiecksmatrix? Was ist eine obere Dreiecksmatrix, was eine untere?</li> <li>Was ist Stellenausl&ouml;schung? Nenne ein Beispiel!</li> </ul> <h3>&Uuml;bungsbl&auml;tter</h3> <p>Die Aufgabenblätter stehen <a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/seite/uebnuminfing#%C3%9Cbungsbl%C3%A4tter">hier</a>.</p> <table> <tr> <th>#</th> <th>Stoff</th> </tr> <tr> <td>1</td> <td>LR-Zerlegung, Normen</td> </tr> <tr> <td>2</td> <td>Konditionszahl einer Matrix, Stellenausl&ouml;schung, relativer Fehler</td> </tr> <tr> <td>3</td> <td>-</td> </tr> <tr> <td>4</td> <td>LR-Zerlegung, Gau&szlig;-Elimination mit Spaltenpivotwahl</td> </tr> <tr> <td>5</td> <td><a href="../wie-berechnet-man-die-cholesky-zerlegung/">Cholesky-Zerlegung</a></td> </tr> <tr> <td>6</td> <td>Nichtlineare Gleichungssysteme, Newton-Verfahren</td> </tr> <tr> <td>7</td> <td>Fixpunktiteration, Polynomauswertung, Interpolation</td> </tr> <tr> <td>8</td> <td>Tschebyscheff-Polynom, Interpolation</td> </tr> <tr> <td>9</td> <td>Splines</td> </tr> <tr> <td>10</td> <td>Bernstein-Polynom, Bezier-Kurven</td> </tr> <tr> <td>11</td> <td>Quadraturformeln</td> </tr> </table> <h2>Material</h2> <ul> <li><a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/de">Vorlesungswebsite</a></li> <li><a href="https://ankiweb.net/shared/info/3163682033">Mein Anki-Deck</a> (nur 12 Karten)</li> <li><a href="../polynomial-interpolation/">Polynom- und Spline-Interpolation</a>: Ein interaktives Beispiel</li> <li><a href="http://schickling.github.io/algorithms/#/">schickling.github.io</a>: Viele Implementierungen</li> <li>Pseudocode <ul> <li><a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/source-code/Pseudocode/Cholesky-Zerlegung">Cholesky-Zerlegung</a>, siehe <a href="../wie-berechnet-man-die-cholesky-zerlegung/">Artikel</a></li> </ul> </li> <li>StackExchange: <ul> <li><a href="http://math.stackexchange.com/q/430141/6876">How do the different ancillary conditions for splines differ?</a></li> </ul> </li> </ul> <h2>Aufbau der Klausur</h2> <ul> <li>Aufgabe 1: LR-Zerlegung oder Cholesky-Zerlegung; Gau&szlig;-Elimination mit Spaltenpivotwahl; L&ouml;sen eines LGS</li> <li>Aufgabe 2: Nicht-lineare Gleichungssysteme, Fixpunktiteration, Newton-Verfahren</li> <li>Aufgabe 3: <ul> <li>a) Polynominterpolation mit Lagrange-Polynomen</li> <li>b) Newton-Darstellung des Polynoms bestimmen</li> </ul> </li> <li>Aufgabe 4: Quadraturformel herleiten und Integral n&auml;herungsweise berechnen</li> <li>Aufgabe 5: Ordnungsbedingungen, S&auml;tze 27 - 31</li> </ul> <h2>&Uuml;bungsbetrieb</h2> <ul> <li>Wo sind die &Uuml;bungsbl&auml;tter: <a href="http://www.math.kit.edu/ianm3/lehre/numainfing2013s/seite/uebnuminfing">Link</a></li> <li>Abgabeform: nur Handschriftlich</li> <li>Abgabe: Mittwochs, in der Vorlesung</li> <li>R&uuml;cknahme: Freitags, in der &Uuml;bung</li> <li>Turnus: w&ouml;chentlich</li> <li>&Uuml;bungsschein verpflichtend: Ja</li> <li>Bonus durch &Uuml;bungsschein: Nein</li> </ul> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Dienstag, den 24. September 2013 von 11:00 bis 13:00 Uhr <strong>Ort</strong>: steht seit dem 11.09.2013 fest: Klausureinteilung entsprechend des Anfangsbuchstabens des Nachnamens:</p> <table> <tr> <td>Benz-H&ouml;rsaal (10.21)</td><td>A-C</td> </tr> <tr> <td>Daimler-H&ouml;rsaal (10.21)</td><td>D-G und <strong>I</strong></td> </tr> <tr> <td>Neue Chem. (30.46)</td><td>J-L</td> </tr> <tr> <td>Gerthsen-H&ouml;rsaal (30.21)</td><td><strong>H</strong> und M-R</td> </tr> <tr> <td>HS. a. F. (50.35)</td><td>S-Z</td> </tr> </table> <p><strong>Punkte</strong>: ?<br /> <strong>Bestehensgrenze</strong>: ?<br /> <strong>Übungsschein</strong>: Verpflichtend (ist inzwischen auch eingetragen)<br /> <strong>Bonuspunkte</strong>: Gibt es nicht<br /> <strong>Einsicht</strong>: Termin noch nicht bekannt (Stand: 22.09.2013)<br /></p> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> <p>Sind noch nicht draußen (Stand: 22.09.2013)</p> What does #!/usr/bin/python mean? //martin-thoma.com/what-does-usrbinpython-mean/ Tue, 16 Apr 2013 18:23:17 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-does-usrbinpython-mean <p>You’ve probably already seen one of the following lines:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">#!/bin/sh #!/usr/bin/python #!/usr/bin/python3 #!/usr/bin/env python #!/usr/bin/perl #!/usr/bin/php #!/usr/bin/ruby</code></pre></div> <p>This is a <a href="http://en.wikipedia.org/wiki/Shebang_%28Unix%29">shebang</a>. It’s a directive for your command line interpreter how it should execute a script.</p> <p>For example, you have a file with this content:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python3</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">sys</span> <span class="k">print</span><span class="p">(</span><span class="n">sys</span><span class="o">.</span><span class="n">version_info</span><span class="p">)</span></code></pre></div> <p>Now you can execute it via <code>python3 yourFile.py</code>. But alternatively, you can make it executable and simply type <code>./yourFile.py</code></p> <p>By the way, you should use <code>#!/usr/bin/env python</code> <a href="http://stackoverflow.com/q/1352922/562769">for some reasons</a>.</p> Colors in Vim //martin-thoma.com/colors-in-vim/ Tue, 09 Apr 2013 17:36:31 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/colors-in-vim <h2>ANSI Color codes</h2> <table> <tr> <td style="background: black;color:white">0</td> <td style="background: maroon;color:white">1</td> <td style="background: green;color:white">2</td> <td style="background: olive;color:white">3</td> <td style="background: navy;color:white">4</td> <td style="background: purple;color:white">5</td> <td style="background: teal;color:white">6</td> <td style="background: silver;color:black">7</td> </tr> </table> <h2>256 colors</h2> <p>You might need to <code>set t_Co=256</code>.</p> <table> <tr> <td style="background:#000000">x016_Grey0</td> <td style="background:#00005f">x017_NavyBlue</td> <td style="background:#000087">x018_DarkBlue</td> <td style="background:#0000af">x019_Blue3</td> </tr> <tr> <td style="background:#0000d7">x020_Blue3</td> <td style="background:#0000ff">x021_Blue1</td> <td style="background:#005f00">x022_DarkGreen</td> <td style="background:#005f5f">x023_DeepSkyBlue4</td> </tr> <tr> <td style="background:#005f87">x024_DeepSkyBlue4</td> <td style="background:#005faf">x025_DeepSkyBlue4</td> <td style="background:#005fd7">x026_DodgerBlue3</td> <td style="background:#005fff">x027_DodgerBlue2</td> </tr> <tr> <td style="background:#008700">x028_Green4</td> <td style="background:#00875f">x029_SpringGreen4</td> <td style="background:#008787">x030_Turquoise4</td> <td style="background:#0087af">x031_DeepSkyBlue3</td> </tr> <tr> <td style="background:#0087d7">x032_DeepSkyBlue3</td> <td style="background:#0087ff">x033_DodgerBlue1</td> <td style="background:#00af00">x034_Green3</td> <td style="background:#00af5f">x035_SpringGreen3</td> </tr> <tr> <td style="background:#00af87">x036_DarkCyan</td> <td style="background:#00afaf">x037_LightSeaGreen</td> <td style="background:#00afd7">x038_DeepSkyBlue2</td> <td style="background:#00afff">x039_DeepSkyBlue1</td> </tr> <tr> <td style="background:#00d700">x040_Green3</td> <td style="background:#00d75f">x041_SpringGreen3</td> <td style="background:#00d787">x042_SpringGreen2</td> <td style="background:#00d7af">x043_Cyan3</td> </tr> <tr> <td style="background:#00d7d7">x044_DarkTurquoise</td> <td style="background:#00d7ff">x045_Turquoise2</td> <td style="background:#00ff00">x046_Green1</td> <td style="background:#00ff5f">x047_SpringGreen2</td> </tr> <tr> <td style="background:#00ff87">x048_SpringGreen1</td> <td style="background:#00ffaf">x049_MediumSpringGreen</td> <td style="background:#00ffd7">x050_Cyan2</td> <td style="background:#00ffff">x051_Cyan1</td> </tr> <tr> <td style="background:#5f0000">x052_DarkRed</td> <td style="background:#5f005f">x053_DeepPink4</td> <td style="background:#5f0087">x054_Purple4</td> <td style="background:#5f00af">x055_Purple4</td> </tr> <tr> <td style="background:#5f00d7">x056_Purple3</td> <td style="background:#5f00ff">x057_BlueViolet</td> <td style="background:#5f5f00">x058_Orange4</td> <td style="background:#5f5f5f">x059_Grey37</td> </tr> <tr> <td style="background:#5f5f87">x060_MediumPurple4</td> <td style="background:#5f5faf">x061_SlateBlue3</td> <td style="background:#5f5fd7">x062_SlateBlue3</td> <td style="background:#5f5fff">x063_RoyalBlue1</td> </tr> <tr> <td style="background:#5f8700">x064_Chartreuse4</td> <td style="background:#5f875f">x065_DarkSeaGreen4</td> <td style="background:#5f8787">x066_PaleTurquoise4</td> <td style="background:#5f87af">x067_SteelBlue</td> </tr> <tr> <td style="background:#5f87d7">x068_SteelBlue3</td> <td style="background:#5f87ff">x069_CornflowerBlue</td> <td style="background:#5faf00">x070_Chartreuse3</td> <td style="background:#5faf5f">x071_DarkSeaGreen4</td> </tr> <tr> <td style="background:#5faf87">x072_CadetBlue</td> <td style="background:#5fafaf">x073_CadetBlue</td> <td style="background:#5fafd7">x074_SkyBlue3</td> <td style="background:#5fafff">x075_SteelBlue1</td> </tr> <tr> <td style="background:#5fd700">x076_Chartreuse3</td> <td style="background:#5fd75f">x077_PaleGreen3</td> <td style="background:#5fd787">x078_SeaGreen3</td> <td style="background:#5fd7af">x079_Aquamarine3</td> </tr> <tr> <td style="background:#5fd7d7">x080_MediumTurquoise</td> <td style="background:#5fd7ff">x081_SteelBlue1</td> <td style="background:#5fff00">x082_Chartreuse2</td> <td style="background:#5fff5f">x083_SeaGreen2</td> </tr> <tr> <td style="background:#5fff87">x084_SeaGreen1</td> <td style="background:#5fffaf">x085_SeaGreen1</td> <td style="background:#5fffd7">x086_Aquamarine1</td> <td style="background:#5fffff">x087_DarkSlateGray2</td> </tr> <tr> <td style="background:#870000">x088_DarkRed</td> <td style="background:#87005f">x089_DeepPink4</td> <td style="background:#870087">x090_DarkMagenta</td> <td style="background:#8700af">x091_DarkMagenta</td> </tr> <tr> <td style="background:#8700d7">x092_DarkViolet</td> <td style="background:#8700ff">x093_Purple</td> <td style="background:#875f00">x094_Orange4</td> <td style="background:#875f5f">x095_LightPink4</td> </tr> <tr> <td style="background:#875f87">x096_Plum4</td> <td style="background:#875faf">x097_MediumPurple3</td> <td style="background:#875fd7">x098_MediumPurple3</td> <td style="background:#875fff">x099_SlateBlue1</td> </tr> <tr> <td style="background:#878700">x100_Yellow4</td> <td style="background:#87875f">x101_Wheat4</td> <td style="background:#878787">x102_Grey53</td> <td style="background:#8787af">x103_LightSlateGrey</td> </tr> <tr> <td style="background:#8787d7">x104_MediumPurple</td> <td style="background:#8787ff">x105_LightSlateBlue</td> <td style="background:#87af00">x106_Yellow4</td> <td style="background:#87af5f">x107_DarkOliveGreen3</td> </tr> <tr> <td style="background:#87af87">x108_DarkSeaGreen</td> <td style="background:#87afaf">x109_LightSkyBlue3</td> <td style="background:#87afd7">x110_LightSkyBlue3</td> <td style="background:#87afff">x111_SkyBlue2</td> </tr> <tr> <td style="background:#87d700">x112_Chartreuse2</td> <td style="background:#87d75f">x113_DarkOliveGreen3</td> <td style="background:#87d787">x114_PaleGreen3</td> <td style="background:#87d7af">x115_DarkSeaGreen3</td> </tr> <tr> <td style="background:#87d7d7">x116_DarkSlateGray3</td> <td style="background:#87d7ff">x117_SkyBlue1</td> <td style="background:#87ff00">x118_Chartreuse1</td> <td style="background:#87ff5f">x119_LightGreen</td> </tr> <tr> <td style="background:#87ff87">x120_LightGreen</td> <td style="background:#87ffaf">x121_PaleGreen1</td> <td style="background:#87ffd7">x122_Aquamarine1</td> <td style="background:#87ffff">x123_DarkSlateGray1</td> </tr> <tr> <td style="background:#af0000">x124_Red3</td> <td style="background:#af005f">x125_DeepPink4</td> <td style="background:#af0087">x126_MediumVioletRed</td> <td style="background:#af00af">x127_Magenta3</td> </tr> <tr> <td style="background:#af00d7">x128_DarkViolet</td> <td style="background:#af00ff">x129_Purple</td> <td style="background:#af5f00">x130_DarkOrange3</td> <td style="background:#af5f5f">x131_IndianRed</td> </tr> <tr> <td style="background:#af5f87">x132_HotPink3</td> <td style="background:#af5faf">x133_MediumOrchid3</td> <td style="background:#af5fd7">x134_MediumOrchid</td> <td style="background:#af5fff">x135_MediumPurple2</td> </tr> <tr> <td style="background:#af8700">x136_DarkGoldenrod</td> <td style="background:#af875f">x137_LightSalmon3</td> <td style="background:#af8787">x138_RosyBrown</td> <td style="background:#af87af">x139_Grey63</td> </tr> <tr> <td style="background:#af87d7">x140_MediumPurple2</td> <td style="background:#af87ff">x141_MediumPurple1</td> <td style="background:#afaf00">x142_Gold3</td> <td style="background:#afaf5f">x143_DarkKhaki</td> </tr> <tr> <td style="background:#afaf87">x144_NavajoWhite3</td> <td style="background:#afafaf">x145_Grey69</td> <td style="background:#afafd7">x146_LightSteelBlue3</td> <td style="background:#afafff">x147_LightSteelBlue</td> </tr> <tr> <td style="background:#afd700">x148_Yellow3</td> <td style="background:#afd75f">x149_DarkOliveGreen3</td> <td style="background:#afd787">x150_DarkSeaGreen3</td> <td style="background:#afd7af">x151_DarkSeaGreen2</td> </tr> <tr> <td style="background:#afd7d7">x152_LightCyan3</td> <td style="background:#afd7ff">x153_LightSkyBlue1</td> <td style="background:#afff00">x154_GreenYellow</td> <td style="background:#afff5f">x155_DarkOliveGreen2</td> </tr> <tr> <td style="background:#afff87">x156_PaleGreen1</td> <td style="background:#afffaf">x157_DarkSeaGreen2</td> <td style="background:#afffd7">x158_DarkSeaGreen1</td> <td style="background:#afffff">x159_PaleTurquoise1</td> </tr> <tr> <td style="background:#d70000">x160_Red3</td> <td style="background:#d7005f">x161_DeepPink3</td> <td style="background:#d70087">x162_DeepPink3</td> <td style="background:#d700af">x163_Magenta3</td> </tr> <tr> <td style="background:#d700d7">x164_Magenta3</td> <td style="background:#d700ff">x165_Magenta2</td> <td style="background:#d75f00">x166_DarkOrange3</td> <td style="background:#d75f5f">x167_IndianRed</td> </tr> <tr> <td style="background:#d75f87">x168_HotPink3</td> <td style="background:#d75faf">x169_HotPink2</td> <td style="background:#d75fd7">x170_Orchid</td> <td style="background:#d75fff">x171_MediumOrchid1</td> </tr> <tr> <td style="background:#d78700">x172_Orange3</td> <td style="background:#d7875f">x173_LightSalmon3</td> <td style="background:#d78787">x174_LightPink3</td> <td style="background:#d787af">x175_Pink3</td> </tr> <tr> <td style="background:#d787d7">x176_Plum3</td> <td style="background:#d787ff">x177_Violet</td> <td style="background:#d7af00">x178_Gold3</td> <td style="background:#d7af5f">x179_LightGoldenrod3</td> </tr> <tr> <td style="background:#d7af87">x180_Tan</td> <td style="background:#d7afaf">x181_MistyRose3</td> <td style="background:#d7afd7">x182_Thistle3</td> <td style="background:#d7afff">x183_Plum2</td> </tr> <tr> <td style="background:#d7d700">x184_Yellow3</td> <td style="background:#d7d75f">x185_Khaki3</td> <td style="background:#d7d787">x186_LightGoldenrod2</td> <td style="background:#d7d7af">x187_LightYellow3</td> </tr> <tr> <td style="background:#d7d7d7">x188_Grey84</td> <td style="background:#d7d7ff">x189_LightSteelBlue1</td> <td style="background:#d7ff00">x190_Yellow2</td> <td style="background:#d7ff5f">x191_DarkOliveGreen1</td> </tr> <tr> <td style="background:#d7ff87">x192_DarkOliveGreen1</td> <td style="background:#d7ffaf">x193_DarkSeaGreen1</td> <td style="background:#d7ffd7">x194_Honeydew2</td> <td style="background:#d7ffff">x195_LightCyan1</td> </tr> <tr> <td style="background:#ff0000">x196_Red1</td> <td style="background:#ff005f">x197_DeepPink2</td> <td style="background:#ff0087">x198_DeepPink1</td> <td style="background:#ff00af">x199_DeepPink1</td> </tr> <tr> <td style="background:#ff00d7">x200_Magenta2</td> <td style="background:#ff00ff">x201_Magenta1</td> <td style="background:#ff5f00">x202_OrangeRed1</td> <td style="background:#ff5f5f">x203_IndianRed1</td> </tr> <tr> <td style="background:#ff5f87">x204_IndianRed1</td> <td style="background:#ff5faf">x205_HotPink</td> <td style="background:#ff5fd7">x206_HotPink</td> <td style="background:#ff5fff">x207_MediumOrchid1</td> </tr> <tr> <td style="background:#ff8700">x208_DarkOrange</td> <td style="background:#ff875f">x209_Salmon1</td> <td style="background:#ff8787">x210_LightCoral</td> <td style="background:#ff87af">x211_PaleVioletRed1</td> </tr> <tr> <td style="background:#ff87d7">x212_Orchid2</td> <td style="background:#ff87ff">x213_Orchid1</td> <td style="background:#ffaf00">x214_Orange1</td> <td style="background:#ffaf5f">x215_SandyBrown</td> </tr> <tr> <td style="background:#ffaf87">x216_LightSalmon1</td> <td style="background:#ffafaf">x217_LightPink1</td> <td style="background:#ffafd7">x218_Pink1</td> <td style="background:#ffafff">x219_Plum1</td> </tr> <tr> <td style="background:#ffd700">x220_Gold1</td> <td style="background:#ffd75f">x221_LightGoldenrod2</td> <td style="background:#ffd787">x222_LightGoldenrod2</td> <td style="background:#ffd7af">x223_NavajoWhite1</td> </tr> <tr> <td style="background:#ffd7d7">x224_MistyRose1</td> <td style="background:#ffd7ff">x225_Thistle1</td> <td style="background:#ffff00">x226_Yellow1</td> <td style="background:#ffff5f">x227_LightGoldenrod1</td> </tr> <tr> <td style="background:#ffff87">x228_Khaki1</td> <td style="background:#ffffaf">x229_Wheat1</td> <td style="background:#ffffd7">x230_Cornsilk1</td> <td style="background:#ffffff">x231_Grey100</td> </tr> <tr> <td style="background:#080808">x232_Grey3</td> <td style="background:#121212">x233_Grey7</td> <td style="background:#1c1c1c">x234_Grey11</td> <td style="background:#262626">x235_Grey15</td> </tr> <tr> <td style="background:#303030">x236_Grey19</td> <td style="background:#3a3a3a">x237_Grey23</td> <td style="background:#444444">x238_Grey27</td> <td style="background:#4e4e4e">x239_Grey30</td> </tr> <tr> <td style="background:#585858">x240_Grey35</td> <td style="background:#626262">x241_Grey39</td> <td style="background:#6c6c6c">x242_Grey42</td> <td style="background:#767676">x243_Grey46</td> </tr> <tr> <td style="background:#808080">x244_Grey50</td> <td style="background:#8a8a8a">x245_Grey54</td> <td style="background:#949494">x246_Grey58</td> <td style="background:#9e9e9e">x247_Grey62</td> </tr> <tr> <td style="background:#a8a8a8">x248_Grey66</td> <td style="background:#b2b2b2">x249_Grey70</td> <td style="background:#bcbcbc">x250_Grey74</td> <td style="background:#c6c6c6">x251_Grey78</td> </tr> <tr> <td style="background:#d0d0d0">x252_Grey82</td> <td style="background:#dadada">x253_Grey85</td> <td style="background:#e4e4e4">x254_Grey89</td> <td style="background:#eeeeee">x255_Grey93</td> </tr> </table> <h2>Colorize Vim</h2> <p>You can highlight your current line by adding the following line to your <strong>.vimrc</strong>: <code>hi CursorLine cterm=NONE ctermbg=187</code></p> <p>The following line will use color 0 (black) for the text color of the line numbers and color 187 (see above) for the background. <code>highlight LineNr ctermfg=0 ctermbg=187</code></p> KV-Diagramme //martin-thoma.com/kv-diagramme/ Mon, 25 Mar 2013 23:37:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/kv-diagramme <div class="info">Ich setze im Folgenden vorraus, dass man schon mal was von KV-Diagrammen geh&ouml;rt hat und vielleicht schon ein paar gezeichnet hat. Insbesondere erkl&auml;re ich nicht wie man aus dem KV-Diagramm der Gr&ouml;&szlig;e 16 eines der Gr&ouml;&szlig;e 32 bekomt und was die Beschriftung bedeutet.</div> <p>KV-Diagramme sind für die TI-Klausur am KIT bei Herrn Prof. Dr. Asfour sehr wichtig. Im folgenden sind die wichtigsten Eigenschaften, die so explizit leider nicht in der Vorlesung genannt wurden.</p> <h2>Konstruktion aus Schaltfunktion</h2> <p>Gegeben sei folgende vollständig definierte Schaltfunktion: <code>$f(w,x,y,z) := (w \lor \bar y) (\bar w \lor x \lor y) (\bar w \lor \bar x \lor z)$</code></p> <p>Nun kann man eine Funktionstabelle aufstellen:</p> <ol> <li>Dabei schreibt man sich erst das Ger&uuml;st hin, also eine Titelzeile mit den vier Variablen `$w,x,y,z$` und `$2^4 = 16$` Zeilen f&uuml;r die verschiedenen Funktionswerte. Wir brauchen jeweils eine Spalte f&uuml;r die vier Variablen, eine f&uuml;r den Funktionswert `$f(w,x,y,z)$` und am besten noch eine mit der Nummer.</li> <li>Nun z&auml;hlen wir f&uuml;r die vier Variablen bin&auml;r hoch. Dabei einsprechen die konkatenierten Ziffern der Variablen der Spalte &bdquo;Nummer&ldquo;. Ich fine es am einfachsten, dies Spaltenweise zu schreiben. Also 8 Nullen, 8 Einsen f&uuml;r `$w$`. Dann 4 Nullen, 4 Einsen, 4 Nullen, 4 Einsen f&uuml;r `$x$` usw.</li> <li>Als letztes schauen wir uns die drei geklammerten Terme von oben an und schauen, wann diese jeweils Null sind. In die entsprechenden Zeilen der Tabelle tragen wir eine Null ein. In alle &Uuml;brigen kommt eine Eins.</li> </ol> <table> <thead> <tr> <th>Nr</th> <th>`$w$`</th> <th>`$x$`</th> <th>`$y$`</th> <th>`$z$`</th> <th>`$f(w,x,y,z)$`</th> </tr> </thead> <tbody> <tr> <td>0</td> <td>0</td> <td>0</td> <td>0</td> <td>0</td> <td>1</td> </tr> <tr> <td>1</td> <td>0</td> <td>0</td> <td>0</td> <td>1</td> <td>1</td> </tr> <tr> <td>2</td> <td>0</td> <td>0</td> <td>1</td> <td>0</td> <td>0</td> </tr> <tr> <td>3</td> <td>0</td> <td>0</td> <td>1</td> <td>1</td> <td>0</td> </tr> <tr> <td>4</td> <td>0</td> <td>1</td> <td>0</td> <td>0</td> <td>1</td> </tr> <tr> <td>5</td> <td>0</td> <td>1</td> <td>0</td> <td>1</td> <td>1</td> </tr> <tr> <td>6</td> <td>0</td> <td>1</td> <td>1</td> <td>0</td> <td>0</td> </tr> <tr> <td>7</td> <td>0</td> <td>1</td> <td>1</td> <td>1</td> <td>0</td> </tr> <tr> <td>8</td> <td>1</td> <td>0</td> <td>0</td> <td>0</td> <td>0</td> </tr> <tr> <td>9</td> <td>1</td> <td>0</td> <td>0</td> <td>1</td> <td>0</td> </tr> <tr> <td>10</td> <td>1</td> <td>0</td> <td>1</td> <td>0</td> <td>1</td> </tr> <tr> <td>11</td> <td>1</td> <td>0</td> <td>1</td> <td>1</td> <td>1</td> </tr> <tr> <td>12</td> <td>1</td> <td>1</td> <td>0</td> <td>0</td> <td>0</td> </tr> <tr> <td>13</td> <td>1</td> <td>1</td> <td>0</td> <td>1</td> <td>1</td> </tr> <tr> <td>14</td> <td>1</td> <td>1</td> <td>1</td> <td>0</td> <td>0</td> </tr> <tr> <td>15</td> <td>1</td> <td>1</td> <td>1</td> <td>1</td> <td>1</td> </tr> </tbody> </table> <p>Will man diese Tabelle in ein KV-Diagramm übernehmen, muss man nur die Spalte <code>$f(w,x,y,z)$</code> in der richtigen Reihenfolge in die Tabelle füllen. Das macht man, indem man immer bei einem Eckpunkt beginnt und dann eine Z-Form durchgeht:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/karnaugh-map4-300x236.png"><img src="../images/2013/03/karnaugh-map4-300x236.png" alt="KV-Speed-Zeichnen" width="" height="" class="size-medium wp-image-63191" /></a><p class="wp-caption-text">KV-Speed-Zeichnen</p></div> <p>Am Ende sieht es so aus: <img src="../images/2013/03/karnaugh-map1.png" alt="KV-Diagramm" width="512" height="512" class="size-full wp-image-62871" /></p> <h2>Prim- und Kernprimimplikaten</h2> <p>Sei <code>$g(w,x,y,z)$</code> eine Schaltfunktion. <code>$g$</code> ist ein Implikant von <code>$f:\Leftrightarrow \forall_{(w,x,y,z) \in \{0,1\}^4}: g(w,x,y,z) \Rightarrow f(w,x,y,z)$</code>.</p> <p>Ist <code>$g$</code> ist ein Implikant von <code>$f$</code>, so ist <code>$f$</code> ein Implikat von <code>$g$</code>.</p> <p>Das kann man nun sehr schön mit dem KV-Diagramm verknüpfen. Wenn man die beiden Funktionen <code>$f$</code> und <code>$g$</code> in das KV-Diagramm einzeichnet, muss <code>$f$</code> überall dort eine 1 haben, wo <code>$g$</code> eine 1 hat.</p> <p>Was hat es nun mit Primimplikanten auf sich? Wenn man diese Kästchen um 1-Blöcke macht, dann müssen sie jeweils insgesamt genau <code>$2^k, k \in \mathbb{N}_0$</code> Einsen umfassen und dürfen an den Rändern fortgesetz werden (siehe der grüne um 5 und 13). Wenn so ein Block ein Primimplikant ist, darf es keinen größeren Eins-Block geben.</p> <p>Beispiel:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/karnaugh-map2-300x300.png"><img src="../images/2013/03/karnaugh-map2-300x300.png" alt="KV-Diagramm - Beispiel mit Primimplikanten" width="" height="" class="size-medium wp-image-62901" /></a><p class="wp-caption-text">KV-Diagramm - Beispiel mit Primimplikanten</p></div> <p>Das Rosa-Kästchen ist ein Implikant. Es ist jedoch kein Primimplikant, da das blaue Kästchen größer ist. Bis auf das rosa Kästchen und das braune Kästchen sind alle eingezeichenten Kästchen Primimplikanten sein. Es gibt keine weiteren Primimplikanten in dieser Funktion.</p> <p>Nun ist ein Primimplikant ein Kernprimimplikant, wenn er eine 1 überdeckt, die von keinem anderen Primimplikanten überdeckt wird. Das gilt für alle Primimplikanten außer den hellgrünen und den braunen Kästchen.</p> <p>Nochmals für das Beispiel:</p> <p>Primimplikanten sind:</p> <ul> <li>(0,1,5,4) // ganz oben, ist auch Kernprimimplikant</li> <li>(10,11) // 3. Zeile, ist auch Kernprimimplikant</li> <li>(11,15) // 3. Zeile, ist kein Kernprimimplikant</li> <li>(15,13) // 3. Spalte, ist kein Kernprimimplikant</li> <li>(13,5) // 3. Spalte, ist kein Kernprimimplikant</li> </ul> <p>Primimplikate sind:</p> <ul> <li>(2,3,7,6) // 2. Zeile, ist auch Kernprimimplikat</li> <li>(6,14) // 4. Spalte, ist kein Kernprimimplikat</li> <li>(14,12) //4. Spalte, ist kein Kernprimimplikat</li> <li>(8,9) // 4. Zeile, ist auch Kernprimimplikat</li> <li>(8, 12) // 4. Zeile, ist kein Kernprimimplikat</li> </ul> <h2>Hasards</h2> <p>Wie sieht man einen Hasard im KV-Diagramm? Man sucht sich eine Anfangsbelegung und eine Endbelegung. Wenn sich dazwischen <code>$n$</code> Variablen ändern, gibt es <code>$n!$</code> Pfade im KV-Diagram. Ist einer dieser Pfade nicht monoton, so ist dieser Übergang Hasardbehaftet.</p> <p>Nun kann man sich entweder die Funktion selbst im KV-Diagramm anschauen, oder die einzelnen Variablen mit dem Todzeitmodell aufsplitten. Untersucht man ersteres, kann man Funktionshasards finden, bei letzterem Strukturhasards.</p> <p>Nun kann man jeden Hasard noch aufteilen, je nach dem was der Wert der Funktion mit der Anfangsbelegung A bzw. der Wert der Funktion bei der Endbelegung B ist:</p> <ul> <li>`$f(A) = 0 \land f(B) = 0 \Rightarrow$` Statischer 0-Hasard</li> <li>`$f(A) = 0 \land f(B) = 1 \Rightarrow$` Dynamischer 01-Hasard</li> <li>`$f(A) = 1 \land f(B) = 0 \Rightarrow$` Dynamischer 10-Hasard</li> <li>`$f(A) = 1 \land f(B) = 1 \Rightarrow$` Statischer 1-Hasard</li> </ul> <h3>Beispiel</h3> <p>Hier ist ein Beispiel für einen dynamischen 1-0-Hasard:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/karnaugh-map3-300x251.png"><img src="../images/2013/03/karnaugh-map3-300x251.png" alt="Beispiel eines dynamischen 1-0-Hasards" width="" height="" class="size-medium wp-image-63011" /></a><p class="wp-caption-text">Beispiel eines dynamischen 1-0-Hasards</p></div> <h2>Fallstricke</h2> <p>Bei dem Suchen nach Eins- oder Nullblöcken darf man an den Spiegelachsen springen:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/kv-diagramm-fallstrick-1-300x180.png"><img src="../images/2013/03/kv-diagramm-fallstrick-1-300x180.png" alt="KV Diagramm: Fallstrick 1" width="" height="" class="size-medium wp-image-63151" /></a><p class="wp-caption-text">KV Diagramm: Fallstrick 1<br />Quelle: <a href="http://ti.ira.uka.de/Klausur/AlteKlausuren/m_ss_10.pdf#page=2">Klausur vom SS 2010 (KIT)</a></p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/kv-diagramm-fallstrick-2-300x173.png"><img src="../images/2013/03/kv-diagramm-fallstrick-2-300x173.png" alt="KV Diagramm: Fallstrick 2" width="" height="" class="size-medium wp-image-63161" /></a><p class="wp-caption-text">KV Diagramm: Fallstrick 2<br />Quelle: <a href="http://ti.ira.uka.de/Klausur/AlteKlausuren/m_ss_10.pdf#page=2">Klausur vom SS 2010 (KIT)</a></p></div> What does volatile mean? //martin-thoma.com/what-does-volatile-mean/ Wed, 20 Mar 2013 22:19:41 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-does-volatile-mean <p>You might have read the variable modifier <code>volatile</code> in C, C++ or in Java. But do you know what it means?</p> <h2>C Programming Language</h2> <p>The C Programming language by Kerninghan and Ritchie (second edition) contains this keyword only 13 times. Here are the most important ones:</p> <blockquote>[...] declaring it volatile announces that it has special properties relevant to optimization. Neither qualifier affects the range of values or arithmetic properties of the object. Qualifiers are discussed in Par.A.8.2.</blockquote> <p>Page 158</p> <blockquote>The purpose of volatile is to force an implementation to suppress optimization that could otherwise occur. For example, for a machine with memory-mapped input/output, a pointer to a device register might be declared as a pointer to volatile, in order to prevent the compiler from removing apparently redundant references through the pointer. Except that it should diagnose explicit attempts to change const objects, a compiler may ignore these qualifiers.</blockquote> <p>Page 172</p> <h2>Java</h2> <p>Java Language Specification actually covers this quite good:</p> <blockquote>The Java programming language allows threads to access shared variables (&sect;17.1). As a rule, to ensure that shared variables are consistently and reliably updated, a thread should ensure that it has exclusive use of such variables by obtaining a lock that, conventionally, enforces mutual exclusion for those shared variables. The Java programming language provides a second mechanism, volatile fields, that is more convenient than locking for some purposes. A field may be declared volatile, in which case the Java Memory Model ensures that all threads see a consistent value for the variable (&sect;17.4).</blockquote> <p>Ok, so in Java it is important for multithreading. The example 8.3.1.4-1 of the <a href="http://docs.oracle.com/javase/specs/">JLS 7.0</a> is also very interesting.</p> <blockquote>A write to a volatile field (&sect;8.3.1.4) happens-before every subsequent read of that field.</blockquote> <blockquote>For the purposes of the Java programming language memory model, a single write to a non-volatile long or double value is treated as two separate writes: one to each 32-bit half. This can result in a situation where a thread sees the first 32 bits of a 64-bit value from one write, and the second 32 bits from another write. Writes and reads of volatile long and double values are always atomic.</blockquote> <h2>When do you need it volatile?</h2> <div class="warning">I'm not sure if it is correct what I write here. It makes sense, but please leave a note in comments when I'm wrong.</div> <h3>Thermometer</h3> <p>Imagine you want to build your own thermometer. So you have to access hardware. Now you only want to print the temperature periodically. Something like this:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#include &lt;unistd.h&gt;</span> <span class="kt">int</span> <span class="nf">getTemperature</span><span class="p">()</span> <span class="p">{</span> <span class="c1">// accessing the hardware device register happens here</span> <span class="k">return</span> <span class="mi">42</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="mi">60</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">temperature</span> <span class="o">=</span> <span class="n">getTemperature</span><span class="p">();</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Temperature: %i &amp;deg;C</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">temperature</span><span class="p">);</span> <span class="n">sleep</span><span class="p">(</span><span class="mi">2</span><span class="p">);</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Now, as you always access the same register and you don’t change it, the CPU could cache the result. That would be bad, because another source (the hardware) changes the value. So you don’t want to cache it. This is - if I understand it correctly - what volatile is good for. It makes sure that you really access memory and not some registers, because it got optimized or cached.</p> <h3>I / O</h3> <p>Imagine you write an application that want to transfer data from a disk to another disk. You might have one producer and one consumer. The producer tries to get data from the disk. Lets say the disk has a buffer and a register that indicates how many blocks are in the buffer. So your producer might poll at some point:</p> <p><code>int register = 0; while(register == 0);</code></p> <p>Now the register can get changed by the device, but it seems to be an obvious that you can optimize this to</p> <p><code>while(TRUE);</code></p> <p>Now, with this “optimization” that the compiler might make, you will never notice when you can read from the disk. So you would mark register as volatile to tell the compiler that he should not optimize it.</p> <p>Do you know some better examples? Perhaps short C examples with real code where you can actually see the difference?</p> <h2>Further reading</h2> <ul> <li><a href="http://stackoverflow.com/q/3488703/562769">When exactly do you use the volatile keyword in Java?</a></li> <li><a href="http://stackoverflow.com/a/3430809/562769">Different meaning in Java and C#</a></li> </ul> C Puzzle #3 //martin-thoma.com/c-puzzle-3/ Sat, 16 Mar 2013 14:54:43 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/c-puzzle-3 <p>What is the output of the following programm?</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include&lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;%i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="o">-</span><span class="mi">13</span><span class="o">&gt;&gt;</span><span class="mi">1</span><span class="p">);</span> <span class="p">}</span></code></pre></div> <p>.<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /> .<br /></p> <h2>Short answer</h2> <p>-7</p> <h2>Long answer</h2> <blockquote>Signed integers are two&rsquo;s complement binary values that can be used to represent both positive and negative integer values.</blockquote> <p>Source: <a href="http://download.intel.com/products/processor/manual/325462.pdf#page=82">Intels IA-32 Architectures Software Developer’s Manuals</a>, page 83</p> <p>When you want to get the two’s complement representation of -13, you have to get the binary representation of 13, invert the digits and add one. As 13 is 1101 in binary, -13 looks like this on a 32 bit machine: 1111.1111.1111.1111.1111.1111.1111.0011</p> <p>So two results might be logical: 0111.1111.1111.1111.1111.1111.1111.1001</p> <p>or</p> <p>1111.1111.1111.1111.1111.1111.1111.1001</p> <p>Lets get the assembly code:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gcc -S -O0 test.c</code></pre></div> <div class="highlight"><pre><code class="language-text" data-lang="text">.file &quot;test.c&quot; .section .rodata .LC0: .string &quot;%i\n&quot; .text .globl main .type main, @function main: .LFB0: .cfi_startproc pushl %ebp .cfi_def_cfa_offset 8 .cfi_offset 5, -8 movl %esp, %ebp .cfi_def_cfa_register 5 andl `$-16, %esp subl $`16, %esp movl `$-7, 4(%esp) movl $`.LC0, (%esp) call printf leave .cfi_restore 5 .cfi_def_cfa 4, 4 ret .cfi_endproc .LFE0: .size main, .-main .ident &quot;GCC: (Ubuntu/Linaro 4.7.2-2ubuntu1) 4.7.2&quot; .section .note.GNU-stack,&quot;&quot;,@progbits</code></pre></div> <p>In line 18 you can see that the bitshift already happened. When you introduce a variable for <code>a</code>, you can see that the compiler makes use of the assembly command <code>sarl %eax</code> or <code>sarl $2, %eax</code> when you shift by two.</p> <p>When you take a look at Oracles <a href="http://docs.oracle.com/cd/E19455-01/806-3773/806-3773.pdf#page=56">IA-32 Assembly Language Reference Manual</a>, page 56, you find:</p> <blockquote>sar right shifts (signed divides) a byte, word, or long value for a count specified by an immediate value and stores the quotient in that byte, word, or long respectively. The second variation right shifts by a count value specified in the CL register. sar rounds toward negative infinity; <strong>the high-order bit remains unchanged</strong>.</blockquote> <p>This means, 1111.1111.1111.1111.1111.1111.1111.1001 is correct. And that’s -7.</p> Google Reader Alternatives //martin-thoma.com/google-reader-alternatives/ Fri, 15 Mar 2013 23:09:04 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-reader-alternatives <p>On July 1, 2013, Google will retire Google Reader (<a href="http://googleblog.blogspot.de/2013/03/a-second-spring-of-cleaning.html">source</a>). A first step should be to save your data (especially your subscriptions). You can do that with <a href="https://www.google.com/takeout">Google Takeout</a>. You could also sign a <a href="https://www.change.org/petitions/google-keep-google-reader-running">petition against closing Google Reader</a>, but I doubt that this will have any effect. Currently, 106,712 people support this petition, though.</p> <h2>How I used Google Reader</h2> <p>Most important for me was the Chrome plugin:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-reader-icon.png" class="image"><img src="//martin-thoma.com/captions/google-reader-icon.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Reader in Chrome - Icon indicates number of new items</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-reader-chrome-popup.png" class="image"><img src="//martin-thoma.com/captions/google-reader-chrome-popup.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Reader in Chrome - Show all new items</div></div></li></ul> <p>The website offered a nice, clean way to administrate my 109 Feeds. Last (and least) the Android App. I don’t have my smartphone long enough to really use this app, but it is one of 10 Apps I’ve currently installed.</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-reader-website.png" class="image"><img src="//martin-thoma.com/captions/google-reader-website.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Reader Website</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-reader-android-app.png" class="image"><img src="//martin-thoma.com/captions/google-reader-android-app.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Reader Android App</div></div></li></ul> <p>Now, I am interested in alternatives. They should</p> <ul> <li>allow me to import my subscriptions,</li> <li>have a Google Chrome Extension (in <a href="https://chrome.google.com/webstore?utm_source=chrome-ntp-icon">Chrome Web Store</a>)</li> <li>have an Android App (in <a href="https://play.google.com/store">Android Market</a>)</li> <li>have export options</li> <li>sync my feeds, as I would like to read my feeds on several computers and my smartphone</li> <li>allow me to login via Google OpenID</li> </ul> <h2>Web Services</h2> <h3>The Old Reader</h3> <p><a href="http://theoldreader.com/">The Old Reader</a> is a web service that wants to provide the same service as Google did before.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/theoldreader.com-feeds-import-300x175.png"><img src="../images/2013/03/theoldreader.com-feeds-import-300x175.png" alt="The Old Reader" width="" height="" class="size-medium wp-image-61231" /></a><p class="wp-caption-text">The Old Reader</p></div> <p>Looks pretty good, doesn’t it? But it currently displays the message “There are 27283 users in the import queue ahead of you.”</p> <h3>BazQux Reader</h3> <p><a href="http://bazqux.com/">BazQux Reader</a> seemed to be a real alternative. It allowed me to sign in with Google, import my subscriptions and it looked familiar:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/bazqux.com_-300x222.png"><img src="../images/2013/03/bazqux.com_-300x222.png" alt="BazQux Reader" width="" height="" class="size-medium wp-image-61261" /></a><p class="wp-caption-text">BazQux Reader</p></div> <p>Another point for BazQux: It supports OPML-Export (Click on the icon at the top right corner → Subscriptions → Export OPML)</p> <p>But now the drawbacks:</p> <ul> <li>9 $/year</li> <li>no Chrome plugin</li> <li>no Android App</li> </ul> <h3>Bloglovin'</h3> <div class="warning">Bloglovin sends you emails with your feeds. Those emails don't have an unsubscribe link.</div> <p><a href="http://www.bloglovin.com/">Bloglovin’</a> is another WebService that looks very nice and is free, seems to be a real alternative. While importing my subscriptions, I got a 504 Gateway Time-out, but it imported my feeds anyway.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/bloglovin-300x210.png"><img src="../images/2013/03/bloglovin-300x210.png" alt="bloglovin" width="" height="" class="size-medium wp-image-61271" /></a><p class="wp-caption-text">bloglovin</p></div> <p>The service seems to be free, they have an <a href="https://play.google.com/store/apps/details?id=se.yo.android.bloglovin">Android App</a> and an <a href="https://itunes.apple.com/app/bloglovin/id421818340?mt=8">iPhone App</a>, but no Google Chrome App and I can’t sign in with Google.</p> <p>Bloglovin’ does not provide an export function.</p> <h3>Good Noows</h3> <p>It seems to get better. <a href="http://goodnoows.com/">Good Noows</a> lets me sign in with Google, offers an import function and has a <a href="https://chrome.google.com/webstore/detail/good-noows/deegloljmdbfbjhlimieancmcfombgjj?utm_source=chrome-ntp-icon">Chrome App</a>. I seems to be free.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/goodnoows-300x183.png"><img src="../images/2013/03/goodnoows-300x183.png" alt="Good Noows" width="" height="" class="size-medium wp-image-61291" /></a><p class="wp-caption-text">Good Noows</p></div> <p>However, it has no Android App and seems not to support export.</p> <h3>Bloglines</h3> <p><a href="http://www.bloglines.com/index.html">Bloglines</a> offers an export function! I can’t login with Google, but I can import my 109 Feeds.</p> <p>It looks like this: <a href="../images/2013/03/bloglines.png"><img src="../images/2013/03/bloglines-300x184.png" alt="bloglines" width="300" height="184" class="aligncenter size-medium wp-image-61351" /></a></p> <p>It has no Chrome App and the <a href="https://play.google.com/store/apps/details?id=org.nyquil.rss2bloglines&amp;feature=search_result#?t=W251bGwsMSwyLDEsIm9yZy5ueXF1aWwucnNzMmJsb2dsaW5lcyJd">Android App</a> is possibly not official.</p> <h2>Host yourself</h2> <h3>Selfoss</h3> <p><a href="http://selfoss.aditu.de/">Selfoss</a> gives you the possibility to host your RSS-Aggregator by yourself. It looks quite good, requires only PHP 5.3 and MySQL and mobiles are supported.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/selfoss-300x203.png"><img src="../images/2013/03/selfoss-300x203.png" alt="Screenshot of selfoss" width="" height="" class="size-medium wp-image-68361" /></a><p class="wp-caption-text">Screenshot of selfoss</p></div> <ul> <li>Selfoss: <a href="https://github.com/SSilence/selfoss">GitHub</a>, <a href="http://selfoss.aditu.de/">Download</a></li> </ul> <h3>Tiny Tiny RSS</h3> <p><a href="http://tt-rss.org/redmine/projects/tt-rss/wiki">TT-RSS</a> allows you to host a service similar to Google Reader. This could be an interesting alternative, but currently the demo page is disabled. I’m waiting for reviews of this one.</p> <ul> <li>Tiny Tiny RSS: <a href="https://github.com/gothfox/Tiny-Tiny-RSS">GitHub</a>, <a href="http://tt-rss.org/redmine/projects/tt-rss-android/issues">Issue Tracker</a>, <a href="http://tt-rss.org/redmine/projects/tt-rss/wiki#Download">Download</a>, <a href="https://www.softaculous.com/demos/Tiny_Tiny_RSS">Demo</a></li> <li>Android Client: <a href="https://play.google.com/store/apps/details?id=org.fox.ttrss&amp;feature=search_result">Market</a></li> </ul> <h2>Tried, but no alternative</h2> <ul> <li><a href="https://www.pulse.me/">Pulse</a>: Where can I add RSS-Feeds in this service?</li> <li><a href="http://www.feedafever.com/#account">FeedAFever</a>: Why should I pay for this, when there are free services?</li> <li><a href="http://blog.feedly.com/2013/03/14/google-reader/">Feedly</a>: What is this? Is it a Web service? Is it a standalone software? Do I have to host it myself?</li> <li><a href="http://hivemined.org/#wut">Hivemined</a>: Not ready yet</li> <li><a href="http://www.newsblur.com/">NewsBlur</a>: I could not sign in.</li> <li><a href="https://www.rolio.com/">Rolio.com</a>: No import</li> </ul> <h2>More alternatives</h2> <p>Here is <a href="http://www.anoxa.de/blog2/?p=16012">an article</a> that lists lots of alternatives.</p> <h2>A short survey</h2> <p>I’m interested in your experiences. Would you please participate in this five minute survey?</p> <iframe src="https://docs.google.com/forms/d/1m7-dKZkKGKQrn3fhejKAxMAw-rWjTR8t1hdE3-zZr-8/viewform?embedded=true" width="512" height="500" frameborder="0" marginheight="0" marginwidth="0">Wird geladen...</iframe> Myth: The Internet doesn't forget //martin-thoma.com/myth-the-internet-doesnt-forget/ Thu, 14 Mar 2013 12:01:58 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/myth-the-internet-doesnt-forget <p>I’ve created a <a href="http://www.youtube.com/watch?v=QDV4E9ldelM&amp;list=PL1EB0B7290460E720">playlist</a> with 51 songs on YouTube about two years ago.</p> <p>Let’s see the stats:</p> <ul> <li>6 of 51 are still available</li> <li>5 had copyright problems</li> <li>17 songs are not available because of <a href="http://en.wikipedia.org/wiki/Gesellschaft_f%C3%BCr_musikalische_Auff%C3%BChrungs-_und_mechanische_Vervielf%C3%A4ltigungsrechte">GEMA</a></li> <li>22 are gone for other reasons</li> </ul> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/youtube-gema-300x134.png"><img src="../images/2013/03/youtube-gema-300x134.png" alt="YouTube Video is not available in Germany because of GEMA" width="" height="" class="size-medium wp-image-60991" /></a><p class="wp-caption-text">YouTube Video is not available in Germany because of GEMA</p></div> <table> <thead> <tr> <th>Song</th> <th>Available</th> </tr> </thead> <tbody> <tr> <td><abbr title="Metallica ...; Someday-Ni...; Metallica ...; Metallica - T...">4 songs</abbr></td> <td>This video is no longer available due to a copyright claim by WMG.</td> </tr> <tr> <td><abbr title="Cyanide - Metallic...">1 songs</abbr></td> <td>This video is no longer available due to a copyright claim by Warner Music Group.</td> </tr> <tr> <td><abbr title="I even can't see the full title of that clip">Metallica - T...</abbr></td> <td>Not available in Germany (WMG, GEMA)</td> </tr> <tr> <td><abbr title="Ebay song; Brian McFadden - Real To Me">2 songs</abbr></td> <td>Unfortunately, this SME-music-content is not available in Germany because GEMA has not granted the respective music publishing rights.</td> </tr> <tr> <td><abbr title="The Kooks - Sway">1 songs</abbr></td> <td>Unfortunately, this SME-music-content is not available in Germany because GEMA has not granted the respective music publishing rights.</td> </tr> <tr> <td><abbr title="Within Temptation - Running up that hill; Warlock - F&uuml;r Immer; Smells Like Teen Spirit Misheard; Metallica - Master Of Puppets; The Rasmus - Livin' in a world without you; The Fratellis - (13) Nobody's Favourite Actor; The Fratellis - My Friend John; Blink 182 - All The Small Things; Blink-182 - What's My Age Again?">9 songs</abbr>&lt;/</td> <td>[...] UMG-music-content is not available in Germany because GEMA [...]</td> </tr> <tr> <td><abbr title="Nickelback - Rockstar; Nickelback - Far Away">2 song</abbr></td> <td>Unfortunately, this video is not available in Germany because it may contain music for which GEMA has not granted the respective music rights.</td> </tr> <tr> <td><abbr title="Nightwish - Kinslayer; Wishmaster - The Misheard">2 songs</abbr>&lt;/</td> <td>This video is not available in your country.</td> </tr> <tr> <td><abbr title="I can't see the title of those clips.">11 song</abbr></td> <td>This video is no longer available because the YouTube account associated with this video has been terminated. </td> </tr> <tr> <td><abbr title="I even can't see the title of that clip">3 songs</abbr></td> <td>This video is unavailable.</td> </tr> <tr> <td><abbr title="I even can't see the title of that clip">2 songs</abbr></td> <td>content violated YouTube's Terms of Service</td> </tr> <tr> <td><abbr title="I even can't see the title of those clips">2 songs</abbr></td> <td>This video has been removed by the user.</td> </tr> <tr> <td><abbr title="I even can't see the title of that clip"> 4 songs</abbr></td> <td>This video is private.</td> </tr> <tr> <td>Cheney's Got A Gun</td> <td><a href="http://www.youtube.com/watch?v=7fcYKVj23FU">Available</a>!</td> </tr> <tr> <td>My Favorite Things</td> <td><a href="http://www.youtube.com/watch?v=6C48AMyV64Q">Available</a>!</td> </tr> <tr> <td>Osama Bin Laden Song</td> <td><a href="http://www.youtube.com/watch?v=46OMP4SQCu0">Available</a>!</td> </tr> <tr> <td>Harry Potter Parody Song: Stay - Katy Cartee Haile</td> <td><a href="http://www.youtube.com/watch?v=eEyHtrmNbCs">Available</a>!</td> </tr> <tr> <td>Wii 'Fat' Song</td> <td><a href="http://www.youtube.com/watch?v=pDe7MPPZYgE">Available</a>!</td> </tr> <tr> <td>Billy Talent - Fallen Leaves</td> <td><a href="http://www.youtube.com/watch?v=UJZYKdLJljQ">Available</a>!</td> </tr> </tbody> </table> Nexus 4 //martin-thoma.com/nexus-4/ Sun, 10 Mar 2013 12:52:06 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/nexus-4 <h2>Buying it</h2> <p>You can buy a Nexus 4 in <a href="http://en.wikipedia.org/wiki/Saturn_(store)">Saturn</a>, but the 16GB-version costs 395 Euro there (<a href="http://www.saturn.de/mcs/product/LG-Nexus-4-16-GB,48352,365082,523287.html?langId=-3">source</a>). In Google Play Store, it costs “only” 349 Euro (<a href="https://play.google.com/store/devices/details/Nexus_4_16GB?id=nexus_4_16gb">source</a>).</p> <h3>Comdirect</h3> <p>So, I’ve decided to buy it from Google Play Store. But you have to have a <a href="http://www.google.de/wallet/">Google Wallet</a> account to use it. For a Google Wallet account, you need a credit card. Unlike in the USA, most people in Germany don’t have a credit card. I had to get one and decided to use the free one from <a href="http://de.wikipedia.org/wiki/Comdirect">Comdirect</a>.</p> <p>Here is a list of letters I got… I’ve expected one or two.</p> <dl> <dt>08.02.2013</dt> <dd>I sent my information for registration to comdirect</dd> <dt>15.02.2013</dt> <dd>Notice that I need to send a <a href="http://de.wikipedia.org/wiki/Meldebest%C3%A4tigung">Meldebest&auml;tigung</a> as I did identity verification with my <a href="http://commons.wikimedia.org/wiki/File:Biometrie_reisepass_deutsch.jpg">passport</a> and not with my <a href="http://en.wikipedia.org/wiki/German_identity_card">identity card</a>. The Meldebest&auml;tigung costs 8.00 Euro.</dd> <dt>21.02.2013</dt> <dd>General information like account number</dd> <dt>22.02.2013</dt> <dd>PIN for online login</dd> <dt>28.02.2013</dt> <dd>Visa-Card</dd> <dt>27.02.2013</dt> <dd><a href="http://en.wikipedia.org/wiki/Transaction_authentication_number">iTAN</a> list</dd> <dt>04.03.2013</dt> <dd>.comdirect girocard</dd> <dt>05.03.2013</dt> <dd>re-activation of bank account</dd> <dt>05.03.2013</dt> <dd>bank account blocked: three failed online logins</dd> <dt>05.03.2013</dt> <dd>PIN for <a href="http://en.wikipedia.org/wiki/Girocard">Girocard</a></dd> </dl> <div style="width: 300px" class="wp-caption aligncenter"><a href="../images/2013/03/comdirect-karten-irrsinn.jpg"><img src="//martin-thoma.com/captions/comdirect-karten-irrsinn.jpg" alt="Three cards I got from one bank" width="290" height="300" class="size-medium wp-image-60371" /></a><p class="wp-caption-text">Three cards I got from one bank</p></div> <p>At 28.02.2013, I first transferred 5 Euro to check if everything works as expected. I have to transfer it to my girocard. It arrived at 01.03.2013. Then I have to transfer it to my Visa card. It arrived at 04.03.2013. Quite a long time for an internal transaction.</p> <p>As I made three attempts to login into my online account from comdirect bank, my account was locked. I had to send a fax and ask them to unlock my account! Another Euro for the fax. (By the way, I think this is a security leak. If I wanted to do harm to the bank, I could make lots of accesses to their customers accounts and lock them. I guess it wouldn’t take me more than 30 minutes to write the code and about one day to let it run. Very bad.)</p> <h3>Google Play</h3> <p>Ok, I’ve got a credit card. Now I will have bought a Nexus 4 in a couple of minutes, right? Wrong.</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-mail-from-play-2013-03-06-1047.png" class="image"><img src="//martin-thoma.com/captions/google-mail-from-play-2013-03-06-1047.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Mail from Google Play from 2013-03-06, 10:47</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/invalid-adress-help.png" class="image"><img src="//martin-thoma.com/captions/invalid-adress-help.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Invalid address: Google help</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/invalid-address.png" class="image"><img src="//martin-thoma.com/captions/invalid-address.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Play Store: Invalid address bug</div></div></li></ul> <p>What the hell? They think I live in Helgoland or have military address?</p> <p>Ok, let’s try it again:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-wallet-2013-03-06.png" class="image"><img src="//martin-thoma.com/captions/google-wallet-2013-03-06.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Wallet 2013-03-06</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-wallet-2013-03-06-1055.png" class="image"><img src="//martin-thoma.com/captions/google-wallet-2013-03-06-1055.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Wallet 2013-03-06, 10:55</div></div></li></ul> <p>WTF? Although the transaction was canceled, my bank thinks it happened. I can’t see the transaction in my bank account, though. According to my online bank account, I haven’t reached my limit. But I cannot pay for the “second” phone. That sucks.</p> <p>The next day it worked:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/play-store-versanddatum.png" class="image"><img src="//martin-thoma.com/captions/play-store-versanddatum.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Play Store</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-play-store-2013-03-06-1046.png" class="image"><img src="//martin-thoma.com/captions/google-play-store-2013-03-06-1046.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Play Store 2013-03-06, 10:46</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/google-play-store-2013-03-07.png" class="image"><img src="//martin-thoma.com/captions/google-play-store-2013-03-07.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Google Play Store, 2013-03-07</div></div></li></ul> <p>2013-03-07: Now I have to wait for the phone.</p> <p>2013-03-08: Hurray, it’s here!</p> <p>My old not-so-smart phone and my new Nexus 4:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/nexus-4-motorola.jpg"><img src="//martin-thoma.com/captions/nexus-4-motorola.jpg" alt="Nexus 4 and Motorola W156" width="300" height="298" class="size-medium wp-image-60091" /></a><p class="wp-caption-text">Nexus 4 and Motorola W156</p></div> <h2>Micro-SIM vs. Mini-SIM</h2> <p>Did you know that different SIM cards exist? I didn’t. I’ve learned that I have a Mini-SIM, but you need a Micro-SIM for the Nexus 4.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/gsm-sim-card-evolution-300x93.png"><img src="../images/2013/03/gsm-sim-card-evolution-300x93.png" alt="GSM SIM card evolution" width="" height="" class="size-medium wp-image-60011" /></a><p class="wp-caption-text">GSM SIM card evolution (<a href="http://commons.wikimedia.org/wiki/File:GSM_SIM_card_evolution.svg">source</a>)</p></div> <p>I use a pre-paid card from <a href="http://en.wikipedia.org/wiki/Simyo">simyo</a>. Currently, they offer a free exchange of Mini-SIM-cards to Micro-SIM or Nano-SIM:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/simyo-2013-03-08-1912-300x217.png"><img src="../images/2013/03/simyo-2013-03-08-1912-300x217.png" alt="Simyo: Free Micro-SIM" width="" height="" class="size-medium wp-image-60021" /></a><p class="wp-caption-text">Simyo: Free Micro-SIM</p></div> <p>Phew! I was lucky.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/simyo-sim-karte.jpg"><img src="//martin-thoma.com/captions/simyo-sim-karte.jpg" alt="Simyo Kombi SIM (Mini and Micro SIM)" width="300" height="192" class="size-medium wp-image-61041" /></a><p class="wp-caption-text">Simyo Kombi SIM (Mini and Micro SIM)</p></div> <p>The Micro-SIM-card arrived at 2013-03-14 and will be unlocked the next day.</p> <h2>Beginners questions</h2> <div class="question"> <span class="question">What do those small icons on the top mean?</span> <div class="answer"> Those icons are the notifications. Hold your finger on the top bar and pull down. Now you can view / clear them. </div> </div> <div class="question"> <span class="question">How can I close apps?</span> <div class="answer">See <a href="http://www.technipages.com/galaxy-nexus-how-to-close-apps.html">this answer</a>.</div> </div> <div class="question"> <span class="question">How do I remove widgets?</span> <div class="answer"> <ol> <li>Go to your home screen</li> <li>Leave your finger on the widget for three seconds</li> <li>Move your finger to the appearing "remove"</li> </ol> </div> </div> <div class="question"> <span class="question">How do I open a shell?</span> <div class="answer"> Install <a href="https://play.google.com/store/apps/details?id=jackpal.androidterm">Android Terminal Emulator</a>. (It says quite often "Permission denied") </div> </div> <div class="question"> <span class="question">How can I execute Python?</span> <div class="answer"> Install <a href="https://play.google.com/store/apps/details?id=com.hipipal.qpyplus">QPython+ (Android Python)</a>. (WARNING: This seems to be a beta.) </div> </div> <div class="question"> <span class="question">How can I take screenshots on my Nexus 4?</span> <div class="answer"> Press "Volume down" and "Power" at the same time: <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/how-to-take-screenshot-nexus-4.jpg"><img src="//martin-thoma.com/captions/how-to-take-screenshot-nexus-4.jpg" alt="How to take a screenshot with Nexus 4" width="300" height="288" class="size-medium wp-image-60181" /></a><p class="wp-caption-text">How to take a screenshot with Nexus 4</p></div> </div> </div> <div class="question"> <span class="question">How can I enable Geolocations for my photos?</span> <div class="answer"> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/camera-settings.png" class="image"><img src="//martin-thoma.com/captions/camera-settings.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Camera settings</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/Screenshot_2013-03-09-11-01-11.png" class="image"><img src="//martin-thoma.com/captions/Screenshot_2013-03-09-11-01-11.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Android: Store location setting</div></div></li></ul> </div> </div> <h2>Experiments with Nexus 4</h2> <h3>Photo-Sphere</h3> <p>You can create <a href="http://www.androidcentral.com/check-out-these-awesome-photo-sphere">awesome photos</a> with photo sphere. But objects have to be not very close.</p> <p>Here is my first try with my room:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/my-room-2013-03-08.jpg"><img src="//martin-thoma.com/captions/my-room-2013-03-08.jpg" alt="A sphere photo of my room" width="300" height="150" class="size-medium" /></a><p class="wp-caption-text">A sphere photo of my room</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/Karlsruhe-Panorama_2013-03-09_0930.jpg"><img src="//martin-thoma.com/captions/Karlsruhe-Panorama_2013-03-09_0930.jpg" alt="Karlsruhe Panorama, 2013-03-09 09:30" width="298" height="118" class="size-medium" /></a><p class="wp-caption-text">Karlsruhe Panorama, 2013-03-09 09:30</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/Karlsruhe-Panorama_2013-03-09_0951.jpg"><img src="//martin-thoma.com/captions/Karlsruhe-Panorama_2013-03-09_0951.jpg" alt="Karlsruhe (Panorama) 2013-03-09 09:51" width="299" height="121" class="size-medium" /></a><p class="wp-caption-text">Karlsruhe (Panorama) 2013-03-09 09:51</p></div> <p>[sphere 60431]</p> <p>At the moment, it is not simply possible to include a sphere into a WordPress blog. <a href="https://github.com/kennydude/photosphere">Code</a> was published to create this effect and <a href="http://kennydude.github.com/photosphere/test.html">it works</a>, but <a href="http://wordpress.org/extend/plugins/wp-photo-sphere/">the WordPress plugin</a> has <a href="http://wordpress.org/support/plugin/wp-photo-sphere">some issues</a>.</p> <p>By the way, you can directly create a tiny world image from a photo sphere:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/karlsruhe-tiny-world.jpg"><img src="//martin-thoma.com/captions/karlsruhe-tiny-world.jpg" alt="Karlsruhe - Tiny World" width="300" height="300" class="size-medium" /></a><p class="wp-caption-text">Karlsruhe - Tiny World</p></div> <h3>Adding a nicer alarm</h3> <p>One reason why I bought this phone was that my alarm clock (which is my old phone) is awful. <a href="http://www.zedge.net/ringtones/6067/google-nexus-4-ringtones/0-6-1/">zedge.net</a> seems to be one place where you can get ring tones. I like <a href="http://goo.gl/8c36v">Sintels song</a>, which was in Google Music.</p> <p>I’ve installed <a href="https://play.google.com/store/apps/details?id=com.angryredplanet.android.rings_extended">Rings Extended</a>, as I wasn’t able to find the ringtone without it. That could be better.</p> <h3>Sky Map</h3> <p>As my phone as quite a lot of sensors (GPS, compass, altimeter) I guessed it might be possible to store the well-known stars and show them on the device when you look in their direction. The app is calles “<a href="https://play.google.com/store/apps/details?id=com.google.android.stardroid&amp;hl=en">Sky Map</a>”. I have to try that when the sky is clear.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/android-sky-map-300x180.png"><img src="../images/2013/03/android-sky-map-300x180.png" alt="Android Sky Map" width="" height="" class="size-medium wp-image-60261" /></a><p class="wp-caption-text">Android Sky Map</p></div> <h3>Movies</h3> <p>I was very surprised that they don’t have <a href="../blender-open-movies/">Blender Open Movies</a> in the movie section of play store ☹</p> <h3>MyTracks</h3> <p>MyTracks lets you record the track you take and see some stats about that. Quite nice, but the export doesn’t work.</p> <p>I filed my first bug / feature request for an app: <a href="https://code.google.com/p/mytracks/issues/detail?id=1260">Issue 1260</a></p> <h2>What it replaces</h2> <p>Nexus 4 could replace quite a lot of stuff:</p> <div style="width: 305px" class="wp-caption aligncenter"><a href="../images/2013/03/what-nexus-4-could-replace.jpg"><img src="//martin-thoma.com/captions/what-nexus-4-could-replace.jpg" alt="What Nexus 4 could replace" width="295" height="299" class="size-medium" /></a><p class="wp-caption-text">What Nexus 4 could replace</p></div> <p>But it can’t replace credit cards in Germany as NFC isn’t supported by the shops by now. It can’t really replace a camera as the quality is ugly. Just take a close look at the photo above. This was taken with Nexus 4. Sadly, if you don’t install apps like <a href="https://play.google.com/store/apps/details?id=com.sand.airdroid">AirDroid</a>, it can’t replace a USB stick or a MP3 player. Yes, you can use Google Music and that works, but I would like to be able to copy MP3s from my laptop computer to my smartphone. Directly. With a USB-cable and without having to use the internet. It does replace a notepad, if you only use it for writing texts and not for drawing or math. And, finally, at the moment it doesn’t even replace my old phone because of the SIM-problem I’ve explained above. But as soon as this is fixed, the Nexus 4 will replace my Motorola W156.</p> <p>Here is a comparision of those phones:</p> <table> <thead> <th>&nbsp;</th> <th>Nexus 4</th> <th>Motorola W156</th> </thead> <tbody> <tr> <td>Display</td> <td>4.7 in (120 mm) diagonal IPS<br />1280&times;768 px (316 ppi)</td> <td>1.6 in (40 mm) diagonal<br />128&times;128 pixel</td> </tr> <tr> <td>Colors</td> <td>16 777 216</td> <td>2</td> </tr> <tr> <td>Memory</td> <td>16 GB</td> <td>20 kb (<a href="http://motorolafans.cz/en/phones/motorola-w156.php">source</a>)</td> </tr> <tr> <td>Body</td> <td>133.9 x 68.7 x 9.1 mm</td> <td>114 x 43 x 14 mm</td> </tr> <tr> <td>Weight</td> <td>139 g</td> <td>85 g</td> </tr> <tr> <td>Stand-by time</td> <td>390 hours</td> <td>465 hours</td> </tr> <tr> <td>Battery</td> <td>2100 mAh (Li - Polymer)</td> <td>940 mAh (Li - Ion)</td> </tr> </tbody> </table> <p>Here is the <a href="http://www.phonearena.com/phones/compare/Motorola-W156,Google-Nexus-4/phones/2435,7531">source</a> for that comparison.</p> <p>What it hopefully really replaces are maps. I’ve just downloaded maps for the center of Paris. That were only about 2 MB. Here is a screenshot of maps guidance in action:</p> <div style="width: 190px" class="wp-caption aligncenter"><a href="../images/2013/03/google-maps-on-nexus-4-in-action-180x300.png"><img src="../images/2013/03/google-maps-on-nexus-4-in-action-180x300.png" alt="Google Maps on Nexus 4 in action" width="" height="" class="size-medium wp-image-60561" /></a><p class="wp-caption-text">Google Maps on Nexus 4 in action</p></div> <h2 id="mounting-as-usb-stick">Mounting as USB-Stick</h2> <p>This is a mayor drawback of the Nexus 4. You can’t simply plug it in and work with it like you do with a USB-Stick. You have to enter</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>mkdir Android go-mtpfs Android [do what you want] sudo umount Android </pre></div> </div> </div> <h2>Conclusion</h2> <p>I finally paid 358,99 Euro for the phone and shipping, 8 Euro for the “Meldebestätigung” and 1 Euro for the fax to re-activate my bank account which is 367,99 Euro in total. But if you want to experiment with a high quality smart phone, I guess it’s a good choice.</p> <h2>What's next?</h2> <p>I have some ideas for apps. So my next steps are:</p> <ol> <li>Kick Windows 7 and <a href="https://wiki.archlinux.org/index.php/Installation_Guide">install Arch Linux</a> as the implementation / QA for PSE is over</li> <li><a href="http://developer.android.com/training/index.html">Start developing apps</a></li> <li><a href="http://developer.android.com/distribute/googleplay/publish/register.html">Get Started with Publishing</a></li> </ol> <p>I guess I’ll also write an article what could get improved in Android.</p> Add a new font to ImageMagick //martin-thoma.com/add-a-new-font-to-imagemagick/ Wed, 06 Mar 2013 23:15:26 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/add-a-new-font-to-imagemagick <p>You can list all fonts that are known to ImageMagick by <code>identify -list font</code>. When your font isn’t there, but it is installed, you might want to try these steps:</p> <ul> <li><code>sudo updatedb</code></li> <li>Download <a href="http://www.imagemagick.org/Usage/scripts/imagick_type_gen">imagick_type_gen</a></li> <li>Execute it: <code>perl imagick_type_gen &gt; types.xml</code></li> <li>Copy the result to the folder where it should be <ul> <li><code>locate type.xml</code>. That was <em>/usr/lib/ImageMagick-6.5.7/config/type.xml</em> for me</li> <li><code>sudo cp type.xml /usr/lib/ImageMagick-6.5.7/config/type.xml</code></li> </ul> </li> </ul> <p>You can find some nice fonts <a href="http://www.losttype.com/browse/">here</a>.</p> LaTeX Beamer //martin-thoma.com/latex-beamer/ Tue, 05 Mar 2013 11:25:20 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/latex-beamer <p>I really enjoy creating presentations with LaTeX. The reasons are:</p> <ul> <li>You can use versioning (GIT, SVN, ...)</li> <li>You can use your favorite editor!</li> <li>When you've created an animation with Ti<em>k</em>Z, you can easily go one step back an go through it as fast as it is apropriate!</li> <li>Good separation of presentation and content</li> <li>It compiles to PDF <ul> <li>Everybody can open it</li> <li>It always looks the same (no moved elements or hidden bullet points)</li> </ul> </li> <li>You can use math mode ☺</li> <li>No need to buy anything. It's free and OpenSource.</li> <li>A big community (<a href="http://tex.stackexchange.com/questions/tagged/beamer">StackExchange</a> and <a href="http://www.latex-community.org/forum/viewforum.php?f=3">LateX-Community</a>) helps you, when you got questions.</li> </ul> <p>I’ll now introduce you to the basics of LaTeX beamer presentations. If you only look for example, please go to my <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/presentations">GitHub LaTeX Repository</a>.</p> <h2>Basics</h2> <p>This is a basic presentation:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{beamer} \usetheme{Frankfurt} \usepackage{hyperref} \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[english]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output % of umlauts in pdf \begin{document} \title{The title of your presentation} \subtitle{A subtitle} \author{Martin Thoma} \date{25. March 2013} \subject{Computer Science} \frame{\titlepage} \section{Introduction} \subsection{A subsection!} \begin{frame}{Slide title} Slide content \end{frame} \end{document} </pre></div> </div> </div> <h2>Style</h2> <p>If you want to create nice-looking presentations like <a href="../images/2013/03/tutorium-05.pdf">this one</a> or <a href="../images/2013/03/google-presentation.pdf">that one</a>, you should probably adjust the style. Here is an overview of the default ones that LaTeX has: <a href="http://deic.uab.es/~iblanes/beamer_gallery/">Beamer theme gallery</a> or <a href="http://latex.simon04.net/">here</a>.</p> <p>The important commands for changing the appearance, that should get included just after documentclass, are:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\usetheme{Frankfurt} \usecolortheme{default} </pre></div> </div> </div> <p>When you’re from KIT, you should use the <a href="https://sdqweb.ipd.kit.edu/wiki/Dokumentvorlagen">KIT theme</a>.</p> <p>Here are some screenshots:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 326px; width: 326px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/English-Titlepage.png" class="image"><img src="//martin-thoma.com/captions/English-Titlepage.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">LaTeX Beamer: Example of a titlepage</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/programmieren-tutorium-titlepage.png" class="image"><img src="//martin-thoma.com/captions/programmieren-tutorium-titlepage.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">LaTeX Beamer: Example of a titlepage</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/latex-beamer-quelltext-minted.png" class="image"><img src="//martin-thoma.com/captions/latex-beamer-quelltext-minted.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">LaTeX Beamer: Example of source code</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/03/latex-beamer-uncover-list.png" class="image"><img src="//martin-thoma.com/captions/latex-beamer-uncover-list.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">LaTeX Beamer: Example of a slide</div></div></li></ul> <h2>Sections and subsections</h2> <p>Take a look at the slides I’ve included above. Do you notice the little bubbles at the bottom that indicate how many slides are left?</p> <p>You get the text over the bubbles with <code>\section{Your text}</code> and the bubbles with <code>frame</code>, but you need at least one <code>\subsection{bla}</code>! When you make more than one subsection, the frame-bubbles that belong to the same one get highlighted.</p> <h2>Reveal information</h2> <p>You might want to try those commands to hide and reveal information:</p> <ul> <li><code>\pause</code></li> <li><code>\uncover</code></li> <li><code>\visible</code></li> <li><code>\onslide</code> and <code>\only</code></li> </ul> <p>You can use it like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\begin{frame}{Another title} Some text\\ \uncover&lt;2-&gt;{Uncover me on slide 2 (-)\\} \visible&lt;3-&gt;{visible from slide 3 on (-)\\} \only&lt;4-&gt;{only from slide 4 (-)\\} \onslide&lt;5-&gt;{on slide 5 and further (-)\\} \uncover&lt;6&gt;{Uncover me on slide 6 \\} \visible&lt;7&gt;{visible on 7\\} \only&lt;8&gt;{only on slide 8 \\} \alt&lt;8&gt;{I am on slide 8\\}{I am not on slide 8\\} \onslide&lt;9&gt;{on slide 9\\} \end{frame} </pre></div> </div> </div> <p>Note that the numbers work like <code>\uncover&lt;n-m&gt;{ELEMENT}</code>. If no <code>m</code> is specified, ELEMENT is visible until end of this frame.</p> <p>When you have a list and you want to uncover it element by element, you can use this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\begin{itemize}[&lt;+-&gt;] \item one \item two \item three \end{itemize} </pre></div> </div> </div> <h2>Blocks</h2> <p>You can use <code>block</code>, <code>exampleblock</code> or <code>alertblock</code> inside your frame:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\begin{exampleblock}{Test} This is my text. \end{exampleblock} </pre></div> </div> </div> <p>It looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/latex-beamer-block-300x117.png"><img src="../images/2013/03/latex-beamer-block-300x117.png" alt="LaTeX Beamer blocks: block, exampleblock, alertblock" width="" height="" class="size-medium wp-image-59391" /></a><p class="wp-caption-text">LaTeX Beamer blocks: block, exampleblock, alertblock</p></div> <h2>Images</h2> <p>Quite often, you want to have one big image.</p> <p>You need <code>\usepackage{graphicx}</code> in your preamble.</p> <p>This is how you get the image it:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\begin{frame}{My frame title} \includegraphics[width=\textwidth, height=0.8\textheight, keepaspectratio]{../relative/path/image.jpg} \end{frame} </pre></div> </div> </div> <h2>Further reading</h2> <ul> <li><a href="../sizes-in-latex/" title="Sizes in LaTeX">Sizes in LaTeX</a></li> <li><a href="../how-to-visualize-graph-algorithms-with-latex/" title="How to visualize Graph algorithms with LaTeX">How to visualize Graph algorithms with LaTeX</a></li> <li><a href="http://www.math.umbc.edu/~rouben/beamer/beamer_guide.pdf">UMBC Beamer guide</a></li> <li><code>texdoc beameruserguide</code> or <a href="http://www.tex.ac.uk/tex-archive/macros/latex/contrib/beamer/doc/beameruserguide.pdf">online</a></li> </ul> Linux access rights and attributes //martin-thoma.com/linux-access-rights-and-attributes/ Mon, 04 Mar 2013 22:29:42 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/linux-access-rights-and-attributes <h2>RWX</h2> <h3>Files</h3> <p>Linux files have three important access rights for files:</p> <ul> <li><strong>R</strong>ead</li> <li><strong>W</strong>rite</li> <li>E<strong>x</strong>ecute</li> </ul> <p>If you want to mark a file as executable, you can add the x-right:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>chmod +x </pre></div> </div> </div> <p>When you want to mark a file as readable, you can dd the r-right:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>chmod +r </pre></div> </div> </div> <p>You can remove rights in a similar way:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>chmod -x testfile </pre></div> </div> </div> <p>Now, often this is expressed numerically. Three bits determine if the file is readable (4), writable (2) or executable (1). Did you notice that all of them are powers of two?</p> <h3>Folders</h3> <p>rwx has a meaning for folders, too:</p> <ul> <li><strong>R</strong>ead: if that is missing, you can't use <code>ls</code> in the directory.</li> <li><strong>W</strong>rite: you need this to create new files / folders in the direcotry</li> <li><strong>x</strong> ... like "enter"?: if that is missing, you can't enter the directory.</li> </ul> <h2>User, Group, Others</h2> <p>The rights above can be set for the user who created the file (sometimes also called the owner). Then the group that owns the file and all others. This is the reason why you have three times the rights from above:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:~/Downloads$ ls -l total 29624 drwxr-xr-x 8 moose moose 4096 2013-02-22 14:18 algorithms -rw-r--r-- 1 moose moose 60058 2013-02-11 08:00 args4j-2.0.21.jar drwxr-xr-x 6 moose moose 4096 2013-02-25 20:07 bwinf -rw-r--r-- 1 moose moose 22160041 2013-02-05 16:45 DT2012.zip drwxr-xr-x 8 moose moose 4096 2013-02-28 19:23 graphentheorie -rw-r--r-- 1 moose moose 2164878 2013-02-22 12:38 guava-14.0-rc1.jar -rw-r--r-- 1 moose moose 2705344 2013-03-01 21:07 HardVacuum.zip drwxr-xr-x 8 moose moose 4096 2013-02-05 16:38 informatik-2011 -rw-r--r-- 1 moose moose 111926 2013-02-24 19:09 Jim_Keener_resume.pdf drwxr-xr-x 2 moose moose 4096 2011-11-08 11:50 juniper_linux -rw-r--r-- 1 moose moose 288666 2012-12-04 11:38 junit-4.11.jar drwxr-xr-x 13 moose moose 4096 2013-02-01 23:33 LaTeX-examples drwxr-xr-x 2 moose moose 4096 2009-08-11 17:04 otrdecoder -rw-r--r-- 1 moose moose 728292 2013-03-01 19:33 PlanetCute PNG.zip drwxr-xr-x 2 moose moose 4096 2012-11-13 10:49 ProjectEuler drwxr-xr-x 2 moose moose 4096 2013-03-04 20:28 Screenshots Matlab -rw-r--r-- 1 moose moose 764196 2013-03-04 20:28 Screenshots Matlab.zip -rw-r--r-- 1 moose moose 534614 2013-03-01 19:48 spritelib_gpl.zip drwxr-xr-x 8 moose moose 4096 2013-02-27 18:36 Team drwxr-xr-x 5 moose moose 4096 2013-02-27 19:17 ViMuDat </pre></div> </div> </div> <p>You might wonder what happens when you execute <code>chmod +x filename</code>. Does it set the execute-flag only for the user? Or for all three - user, group, others? Try and find out. You might want to remove all rights with <code>chmod 000 filename</code> before you start.</p> <p>Did you know that you can search for file permissions with <code>find /home/ -perm 777</code>?</p> <h2>SUID, SGID, Sticky Bit</h2> <h3>Files</h3> <p>Sometimes, you want to execute programs as root, although the user who started the execution isn’t root. Take passwd, the program that allows users to change passwords, for example:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:/usr/bin$ ls -l | grep passwd$ -rwsr-xr-x 1 root root 53812 2011-02-14 23:11 gpasswd -rwxr-xr-x 1 root root 13612 2012-11-06 21:41 htpasswd -rwsr-xr-x 1 root lpadmin 13540 2012-12-04 16:24 lppasswd -rwsr-xr-x 1 root root 37140 2011-02-14 23:11 passwd -rwxr-xr-x 1 root root 5070304 2012-04-24 23:38 smbpasswd -rwxr-xr-x 1 root root 9688 2013-01-18 17:59 vino-passwd </pre></div> </div> </div> <p>Instead of “x” in the user-execution-row, it states “s”. That means, you can execute it and it has the SUID-bit set. If “x” wasn’t set, the “S” would be in a capital letter. When you change your password, you need to edit <code>/etc/shadow</code>. This file has very limited access rights: <code>-rw-r-----</code> and is owned by “root” and group “shadow”:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:/etc$ ls -l | grep shadow$ -rw-r----- 1 root shadow 813 2013-01-24 06:21 gshadow -rw-r----- 1 root shadow 1274 2013-01-24 06:21 shadow </pre></div> </div> </div> <p>Here is <a href="http://www.cyberciti.biz/faq/understanding-etcshadow-file/">more about shadow file</a>.</p> <p>The SGID (set group id) bit works similar to the SUID (set user id) bit. When you want to execute something with as the group of the file, you set the SGID bit.</p> <p>The sticky bit seems to be used for programs to stick in memory after it was finished.</p> <p>You can set the sticky bit like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>chmod +t testfile </pre></div> </div> </div> <p>or like that:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>chmod 1777 testfile </pre></div> </div> </div> <h3>Folders</h3> <ul> <li>suid: is ignored on UNIX and Linux systems</li> <li>sgid: new files and subdirectories created within this folder inherit the folders group ID</li> <li>t: when the sticky bit is set, only owners may change the filename or delete files</li> </ul> <h2>Type</h2> <p>The first column of <code>ls -l</code> tells you the type of the item:</p> <ul> <li>-: a file</li> <li>b: a block device</li> <li>c: a character device</li> <li>d: a directory</li> <li>l: a symbolic link</li> <li>p: pipe</li> <li>s: a socket</li> </ul> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:/dev$ ls -l total 0 crw------- 1 root video 10, 175 2013-03-04 10:01 agpgart crw-rw----+ 1 root audio 14, 4 2013-03-04 10:01 audio drwxr-xr-x 2 root root 640 2013-03-04 12:59 block drwxr-xr-x 2 root root 100 2013-03-04 12:59 bsg drwxr-xr-x 3 root root 60 2013-03-04 10:01 bus lrwxrwxrwx 1 root root 3 2013-03-04 10:01 cdrom -&gt; sr0 lrwxrwxrwx 1 root root 3 2013-03-04 10:01 cdrw -&gt; sr0 crw-rw----+ 1 root audio 14, 3 2013-03-04 10:01 dsp lrwxrwxrwx 1 root root 3 2013-03-04 10:01 dvd -&gt; sr0 lrwxrwxrwx 1 root root 3 2013-03-04 10:01 dvdrw -&gt; sr0 crw-rw---- 1 root root 10, 61 2013-03-04 10:01 ecryptfs crw-rw---- 1 root video 29, 0 2013-03-04 10:01 fb0 lrwxrwxrwx 1 root root 13 2013-03-04 10:01 fd -&gt; /proc/... crw-rw-rw- 1 root root 1, 7 2013-03-04 10:01 full crw-rw-rw- 1 root fuse 10, 229 2013-03-04 10:01 fuse crw-rw---- 1 root root 251, 0 2013-03-04 18:14 hidraw0 crw-rw---- 1 root root 10, 228 2013-03-04 10:01 hpet drwxr-xr-x 4 root root 380 2013-03-04 18:14 input crw-rw---- 1 root root 1, 11 2013-03-04 10:01 kmsg srw-rw-rw- 1 root root 0 2013-03-04 10:01 log brw-rw---- 1 root disk 7, 0 2013-03-04 10:01 loop0 [...] </pre></div> </div> </div> <h2>stat</h2> <p>You can display quite a lot of information of a file with stat:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:~/Desktop/Test$ stat testfile File: `testfile' Size: 13 Blocks: 8 IO Block: 4096 regular file Device: 801h/2049d Inode: 923339 Links: 1 Access: (0777/-rwxrwxrwx) Uid: ( 1000/ moose) Gid: ( 1000/moose) Access: 2013-03-04 21:31:52.154187243 +0100 Modify: 2013-03-04 21:31:51.154184098 +0100 Change: 2013-03-04 21:31:51.154184098 +0100 </pre></div> </div> </div> <p>The content of the file is “Hello World.” (12 characters)</p> <h2>Attributes</h2> <p>According to the manpage of chattr:</p> <blockquote>The `c', 's', and `u' attributes are not honored by the ext2 and ext3 filesystems as implemented in the current mainline Linux kernels. These attributes may be implemented in future versions of the ext2 and ext3 filesystems.</blockquote> <h3>Version</h3> <p>I’ve just learned that you can give files version-attributes:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:~/Desktop/Test$ lsattr -v 1338 -----------------e- ./testfile </pre></div> </div> </div> <p>You can set the version like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>chattr -v 1339 testfile </pre></div> </div> </div> <h3>Append only</h3> <p>This one is weird. Theoretically, it should allow me to append to a file, but not to change / delete anything in the file.</p> <p>First of all, I had to use sudo to add this attribute:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo chattr +a testfile </pre></div> </div> </div> <p>Then, I had all permissions:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:~/Desktop/Test$ stat testfile File: `testfile' Size: 13 Blocks: 8 IO Block: 4096 regular file Device: 801h/2049d Inode: 923339 Links: 1 Access: (0777/-rwxrwxrwx) Uid: ( 1000/ moose) Gid: ( 1000/moose) Access: 2013-03-04 21:31:52.154187243 +0100 Modify: 2013-03-04 21:31:51.154184098 +0100 Change: 2013-03-04 21:33:55.154184312 +0100 moose@pc07:~/Desktop/Test$ lsattr -----a-----------e- ./testfile </pre></div> </div> </div> <p>But I couldn’t append to the file with gedit. With bash, it worked fine:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:~/Desktop/Test$ echo &quot;One more line &quot; &gt;&gt; testfile moose@pc07:~/Desktop/Test$ cat testfile Hello World. One more line </pre></div> </div> </div> <p>So I guess I found another bug in gEdit.</p> <h3>Immutable</h3> <p>You can mark a file as immutable with <code>sudo chattr +i testfile</code>. It’s funny, you can’t see that with <code>ls -l</code>, you have to use <code>lsattr</code>. I guess if you manage to get root privileges and want to troll somebody, you could set this bit. I think this might take quite a while until you recognize it.</p> <h3>Secure deletion and undeletable</h3> <p>When secure deletion is set with <code>chattr +s testfile</code> the operating system overwrites the file with random data when it is deleted.</p> <p><code>chattr +u testfile</code> makes your file undeletable. This is strange. You can still delete the file with <code>rm</code>, but the system will not overwrite it. I’ve just <a href="http://unix.stackexchange.com/q/66870/4784">asked a question on SE</a>.</p> <h3>Synchronous update</h3> <p>when you set <code>chattr +S testfile</code> the file gets directly written to the HDD and not buffered by the kernel cache.</p> Check File Systems maximum path depth //martin-thoma.com/check-file-systems-maximum-path-depth/ Sun, 03 Mar 2013 20:51:24 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/check-file-systems-maximum-path-depth <p>Today, I’ve wondered how deep a path could be at maximum. I’ve guessed the file system may be limiting that, but perhaps also some tools that I use for basic operations like listing a folders contents would fail before. So I’ve created the following C-Snippet to test it:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;sys/stat.h&gt;</span> <span class="cp">#include &lt;sys/types.h&gt;</span> <span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#include &lt;string.h&gt;</span> <span class="cp">#include &lt;stdlib.h&gt;</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">int</span> <span class="n">returnCode</span><span class="p">;</span> <span class="kt">char</span> <span class="o">*</span><span class="n">pathname</span><span class="p">;</span> <span class="kt">void</span> <span class="nf">giveInformation</span><span class="p">()</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;return code</span><span class="se">\t\t</span><span class="s">: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">returnCode</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Created sub-directories</span><span class="se">\t</span><span class="s">: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">i</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;length of pathname</span><span class="se">\t</span><span class="s">: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">pathname</span><span class="p">));</span> <span class="k">if</span> <span class="p">(</span><span class="n">strlen</span><span class="p">(</span><span class="n">pathname</span><span class="p">)</span> <span class="o">&lt;=</span> <span class="mi">80</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Path</span><span class="se">\t\t\t</span><span class="s">: %s</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">pathname</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span> <span class="p">()</span> <span class="p">{</span> <span class="n">pathname</span> <span class="o">=</span> <span class="s">&quot;/home/moose/Desktop/Test&quot;</span><span class="p">;</span> <span class="kt">char</span> <span class="o">*</span><span class="n">ext</span> <span class="o">=</span> <span class="s">&quot;/one&quot;</span><span class="p">;</span> <span class="n">returnCode</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">int</span> <span class="n">maxDir</span> <span class="o">=</span> <span class="mi">1000000</span><span class="p">;</span> <span class="k">while</span><span class="p">(</span><span class="n">i</span> <span class="o">&lt;</span> <span class="n">maxDir</span> <span class="o">&amp;&amp;</span> <span class="n">returnCode</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="kt">char</span> <span class="o">*</span><span class="n">newName</span> <span class="o">=</span> <span class="n">malloc</span><span class="p">(</span><span class="n">strlen</span><span class="p">(</span><span class="n">pathname</span><span class="p">)</span><span class="o">+</span><span class="n">strlen</span><span class="p">(</span><span class="n">ext</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">);</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">newName</span><span class="p">,</span> <span class="n">pathname</span><span class="p">);</span> <span class="n">strcat</span><span class="p">(</span><span class="n">newName</span><span class="p">,</span> <span class="n">ext</span><span class="p">);</span> <span class="n">returnCode</span> <span class="o">=</span> <span class="n">mkdir</span><span class="p">(</span><span class="n">newName</span><span class="p">,</span> <span class="mo">0777</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">i</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// if you remove this line, your system gets very slow:</span> <span class="n">free</span><span class="p">(</span><span class="n">pathname</span><span class="p">);</span> <span class="p">}</span> <span class="n">pathname</span> <span class="o">=</span> <span class="n">newName</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">giveInformation</span><span class="p">();</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Now run it:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="sb">`</span><span class="nv">$ </span><span class="nb">time</span> ./createDirectories <span class="k">return</span> code : -1 Created sub-directories : 1018 length of pathname : 4096 real 0m0.281s user 0m0.004s sys 0m0.180s</code></pre></div> <p>Ok, something went wrong at the end. Lets see what crashes when I enter this path in Gnome terminal</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">$`</span> <span class="nb">cd </span>one/one/one .... one/ <span class="sb">`</span><span class="nv">$ </span>mkdir two <span class="nv">$`</span> <span class="nb">cd </span>two <span class="nb">cd</span>: error retrieving current directory: getcwd: cannot access parent directories: File name too long</code></pre></div> <p>Strangely, it showed me a path <code>/home/moose/.../one/one/one/one/tw`$</code>. No, this is not a typo. It showed tw, not two. So, maybe the path can get only that long? Now I created a folder called “three” and one called “this”. I entered both of them with cd, both showed <code>/home/moose/.../one/one/th</code>. So I guess this is a problem of Gnome Terminal and not a limitation of the file system.</p> <p>Let’s see what Nautilus does. I <a href="../cyclic-references-kill-nautilus/" title="Cyclic references kill Nautilus">once got Nautilus to crash</a>, I think I get it another time:</p> <p>Contents, according to nautilus: <code>1,016 items, totalling 4.0 MB</code></p> <p>Then I’ve opened the folder “one” and double clicked as fast as I could. CPU utilization: 100%, but no crash. And 995 items are left ☺ Now a single double click causes 100% CPU utilization for about 25 seconds.</p> <p>When I use a single character for sub-directories, I get:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~/Desktop/Test<span class="nv">$`</span> ./createDirectories <span class="k">return</span> code : -1 Created sub-directories : 2036 length of pathname : 4096</code></pre></div> <h2>Number of directories in one directory</h2> <p>Do you know how many folders can fit into one folder? Well, lets find out:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;sys/stat.h&gt;</span> <span class="cp">#include &lt;sys/types.h&gt;</span> <span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#include &lt;string.h&gt;</span> <span class="cp">#include &lt;stdlib.h&gt;</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">int</span> <span class="n">returnCode</span><span class="p">;</span> <span class="kt">char</span> <span class="o">*</span><span class="n">pathname</span><span class="p">;</span> <span class="cm">/** http://stackoverflow.com/a/440240/562769 */</span> <span class="kt">void</span> <span class="nf">gen_random</span><span class="p">(</span><span class="kt">char</span> <span class="o">*</span><span class="n">s</span><span class="p">,</span> <span class="k">const</span> <span class="kt">int</span> <span class="n">len</span><span class="p">)</span> <span class="p">{</span> <span class="k">static</span> <span class="k">const</span> <span class="kt">char</span> <span class="n">alphanum</span><span class="p">[]</span> <span class="o">=</span> <span class="s">&quot;0123456789&quot;</span> <span class="s">&quot;ABCDEFGHIJKLMNOPQRSTUVWXYZ&quot;</span> <span class="s">&quot;abcdefghijklmnopqrstuvwxyz&quot;</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">len</span><span class="p">;</span> <span class="o">++</span><span class="n">i</span><span class="p">)</span> <span class="p">{</span> <span class="n">s</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">alphanum</span><span class="p">[</span><span class="n">rand</span><span class="p">()</span> <span class="o">%</span> <span class="p">(</span><span class="k">sizeof</span><span class="p">(</span><span class="n">alphanum</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)];</span> <span class="p">}</span> <span class="n">s</span><span class="p">[</span><span class="n">len</span><span class="p">]</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">giveInformation</span><span class="p">()</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;return code</span><span class="se">\t\t</span><span class="s">: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">returnCode</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Created sub-directories</span><span class="se">\t</span><span class="s">: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">i</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;length of pathname</span><span class="se">\t</span><span class="s">: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">pathname</span><span class="p">));</span> <span class="k">if</span> <span class="p">(</span><span class="n">strlen</span><span class="p">(</span><span class="n">pathname</span><span class="p">)</span> <span class="o">&lt;=</span> <span class="mi">80</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Path</span><span class="se">\t\t\t</span><span class="s">: %s</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">pathname</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span> <span class="p">()</span> <span class="p">{</span> <span class="n">pathname</span> <span class="o">=</span> <span class="s">&quot;/home/moose/Desktop/Test/test/&quot;</span><span class="p">;</span> <span class="n">returnCode</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="kt">int</span> <span class="n">maxDir</span> <span class="o">=</span> <span class="mi">1000000</span><span class="p">;</span> <span class="k">while</span><span class="p">(</span><span class="n">i</span> <span class="o">&lt;</span> <span class="n">maxDir</span> <span class="o">&amp;&amp;</span> <span class="n">returnCode</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// get unique name</span> <span class="kt">char</span> <span class="o">*</span><span class="n">foldername</span> <span class="o">=</span> <span class="n">malloc</span><span class="p">(</span><span class="mi">50</span><span class="o">+</span><span class="mi">1</span><span class="p">);</span> <span class="n">gen_random</span><span class="p">(</span><span class="n">foldername</span><span class="p">,</span> <span class="mi">50</span><span class="p">);</span> <span class="kt">char</span> <span class="o">*</span><span class="n">completePath</span> <span class="o">=</span> <span class="n">malloc</span><span class="p">(</span><span class="n">strlen</span><span class="p">(</span><span class="n">pathname</span><span class="p">)</span> <span class="o">+</span><span class="n">strlen</span><span class="p">(</span><span class="n">foldername</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">);</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">completePath</span><span class="p">,</span> <span class="n">pathname</span><span class="p">);</span> <span class="n">strcat</span><span class="p">(</span><span class="n">completePath</span><span class="p">,</span> <span class="n">foldername</span><span class="p">);</span> <span class="n">returnCode</span> <span class="o">=</span> <span class="n">mkdir</span><span class="p">(</span><span class="n">completePath</span><span class="p">,</span> <span class="mo">0777</span><span class="p">);</span> <span class="n">free</span><span class="p">(</span><span class="n">foldername</span><span class="p">);</span> <span class="n">free</span><span class="p">(</span><span class="n">completePath</span><span class="p">);</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">giveInformation</span><span class="p">();</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>I’ve executed it and after eight minutes I canceled the execution.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">$ </span>ls <span class="p">|</span> wc -l 378463</code></pre></div> <p>Ok, not a million folders, but 378.463 is also quite a lot. When I try to open this folder with Nautilus, I get 140% CPU utilization by Nautilus. Quite impressive, for only showing some folders.</p> <p>You should probably not execute the script above, as <a href="http://unix.stackexchange.com/q/66806/4784">deleting the folder isn’t that easy</a>.</p> <p>By the way, I got a new error message that I didn’t know before:</p> <div style="width: 508px" class="wp-caption aligncenter"><a href="../images/2013/03/cannot-move-to-trash-filename.png"><img src="../images/2013/03/cannot-move-to-trash-filename.png" alt="Cannot move file to trash - Filename too long!" width="" height="" class="size-full wp-image-58951" /></a><p class="wp-caption-text">Cannot move file to trash - Filename too long!</p></div> Betriebssysteme Klausur //martin-thoma.com/os-klausur/ Sat, 02 Mar 2013 19:06:15 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/os-klausur <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesungen des Moduls &bdquo;Betriebssysteme&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei Prof. Dr. Bellosa und sp&auml;ter bei Prof. Dr. Beigl geh&ouml;rt.</div> <p>Wenn ich im Folgenden eine Seitenzahl angebe, dann ist damit “Operating System Concepts” von Silberschatz gemeint (ISBN 0-471-69466-5):</p> <h2>Themen</h2> <ul> <li>Process Coordination: <ul> <li>Shared Memory</li> <li>Critical-Section Problem: <a href="http://de.wikipedia.org/wiki/Algorithmus_von_Peterson">Peterson's Solution</a>, Synchronisation</li> <li><a href="http://de.wikipedia.org/wiki/Deadlock">Deadlock</a>, <a href="http://en.wikipedia.org/wiki/Resource_starvation">Starvation</a></li> </ul> </li> <li>Process Management <ul> <li>Process Sheduling</li> <li>Process States: new, ready, running, waiting, terminated</li> <li>Process Control Block: Folie 6/65 slide_proc_management</li> </ul> </li> <li>Memory Management <ul> <li>Globale / lokale Seitenersetzungsstrategie</li> <li>Equal allocation</li> <li><a href="http://de.wikipedia.org/wiki/Slab_allocator">Slab allocator</a></li> </ul> </li> </ul> <h2>Begriffe</h2> <p>Folgende Begriffe muss man kennen und erklären können:</p> <ul> <li>Critical Section und Race Condition</li> <li><a href="http://de.wikipedia.org/wiki/Semaphor_(Informatik)">Semaphor</a>: counting Semaphores, binary Semaphores und Mutex Locks &rarr; Antwort auf S. 200f</li> <li>Dining-Philosophers Problem &rarr; Antwort auf S. 207f</li> <li>Deadlock, Starvation</li> <li>Safe State</li> </ul> <h2>FAQ</h2> <ul> <li>Wie funktionieren Bitmasken und insbesondere ~, &amp;, |?</li> <li>Nenne ein reales Beispiel, bei dem eine Race-Condition auftreten k&ouml;nnte.</li> <li>Welche Probleme hat Contiguous Allocation? &rarr; <span class="hint" title="Man muss sich entscheiden, wo auf der Festplatte eine neue Datei begonnen werden soll; Externe Fragmentierung. Strategien: First Fit, Best Fit, Worst Fit">Antwort</span></li> </ul> <div class="question"> <span class="question">Welche Scheduling-Verfahren gibt es?</span> <div class="answer"> <ul> <li>Priority Scheduling</li> <li>Round Robin</li> <li>Multilevel Feedback Queue</li> <li>Lottery Scheduling</li> <li><abbr title="Preemtitive Shortest Job First">PSJF</abbr></li> <li><abbr title="First Come, First Serve">FCFS</abbr></li> </ul></div> </div> <div class="question"> <span class="question">What is the difference between Page and Frame?</span> <div class="answer">In a paging system, programs and data stored on disk are divided into equal, fixed sized blocks called pages, and main memory is divided into blocks of the same size called frames. Exactly one page can fit in one frame. Physical memory is divided into parts called &bdquo;frame&ldquo; and logical memory is divided into parts called &bdquo;page&ldquo;.</div> Quelle: <a href="http://wiki.answers.com/Q/What_is_the_difference_between_Page_and_Frame">wiki.answers.com</a> </div> <div class="question"> <span class="question">Nennen und erl&auml;utern Sie die drei notwendigen Bedingungen f&uuml;r eine g&uuml;ltige L&ouml;sung des Problems kritischer Abschnitte.</span> <div class="answer"> <ul> <li>Mutual exclusion: Only one thread can be in the CS at a time.</li> <li>Progress: <ul> <li>If no thread is in the CS one of the threads trying to enter will eventually get in</li> <li>Threads that are not trying to enter do not hinder processes that try to enter from getting in</li> </ul> </li> <li>Bounded waiting: Once a thread starts trying to enter the critical section, there is a bound on the number of times other threads get in.</li> </ul> </div> </div> <div class="question"> <span class="question">Wie kann man das Problem kritischer Abschnitte l&ouml;sen?</span> <div class="answer"> <ul> <li>Interrupts deaktivieren (nur im Kernel-Space, nur Single-Core)</li> <li>Spezielle atomare Instruktionen: <ul> <li><a href="http://en.wikipedia.org/wiki/Test-and-set">Test-and-set</a></li> <li><a href="http://en.wikipedia.org/wiki/Compare-and-swap">Compare-and-swap</a></li> <li><a href="http://en.wikipedia.org/wiki/Fetch-and-add">Fetch-and-add</a></li> <li><a href="http://en.wikipedia.org/wiki/Swap_(computer_science)#Dedicated_instructions">swap</a></li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Semaphor_(Informatik)">Semaphor</a> (wait und signal)</li> <li><a href="http://de.wikipedia.org/wiki/Monitor_(Informatik)">Monitor</a></li> <li><a href="http://de.wikipedia.org/wiki/Algorithmus_von_Peterson">Algorithmus von Peterson</a></li> </ul> </div> </div> <div class="question"> <span class="question">Nennen und erkl&auml;ren Sie die ver notwendigen Bedingungen f&uuml;r Deadlocks.</span> <div class="answer"> <ul> <li>Mutual exclusion: Eine Ressource kann nicht gleichzeitig von mehreren Prozessen benutzt werden</li> <li>Hold and wait: Ein Prozess, der bereits mindestens eine Ressource h&auml;lt, wartet auf mindestens eine andere Ressource</li> <li>No preemption: Zugeteilte Ressourcen k&ouml;nnen einem Prozess nicht wieder entzogen werden. Er muss diese selbst freigeben.</li> <li>Circular wait: Es gibt eine Menge von Prozessen `$\{P_0, P_1, \dots, P_n\}$`, wobei `$P_0$` auf eine Ressource wartet, die `$P_1$` h&auml;lt, `$P_1$` auf eine Ressource wartet, die `$P_2$` h&auml;lt, ..., `$P_n$` auf eine Ressource wartet, die `$P_0$` h&auml;lt.</li> </ul> </div> </div> <div class="question"> <span class="question">Was kann man in Bezug auf das Deadlock-Problem machen?</span> <div class="answer"> <ul> <li>Prevention</li> <li>Avoidance</li> <li>Detection: <ul> <li>Prozess abschie&szlig;en</li> <li>Rollback</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Vogel-Strau%C3%9F-Algorithmus">Vogel-Strau&szlig;-Algorithmus</a>: Der User wird sich schon drum k&uuml;mmern, z.B. indem er einen Prozess abschie&szlig;t (<code>kill -9</code>) oder indem er den PC vom Strom nimmt.</li> </ul> </div> </div> <div class="question"> <span class="question">Erkl&auml;ren Sie Raid 0 - 5.</span> <div class="answer"> <ul> <li>Raid 0: Striping. Platten werden "aneinandergeh&auml;ngt".</li> <li>Raid 1: Mirroring. Daten werden auf mehrere Platten gespiegelt.</li> <li>Raid 2: Fehlerkorrigierender Hamming-code.</li> <li>Raid 3: Byteweise Parit&auml;t.</li> <li>Raid 4: Blockweise Parit&auml;t.</li> <li>Raid 5: Blockweise, verteilte Parit&auml;t.</li> </ul> </div> </div> <div class="question"> <span class="question">Warum verwenden wir Seitentabellen? K&ouml;nnte man nicht einfach im Hauptspeicher je zwei Datenw&ouml;rter kombinieren, wobei das erste die Metainformationen (z.B. Zugriffsrechte, Prozess-ID) und das zweite die Daten enth&auml;lt?</span> <div class="answer"> Prinzipiell wollen wir in einer x86-Architektur, dass sich die Hardware um das Paging k&uuml;mmert. Bei MIPS sieht das wohl anders aus (<a href="http://stackoverflow.com/q/10671147/562769">Quelle</a>). Wenn man sich f&uuml;r jedes Datenwort ein Datenwort mit Metainformationen merken w&uuml;rde, h&auml;tte man sehr viel Overhead. Diese Informationen hat man bei Paging auf IA-32 nur jede 4096 Byte! (Allgemein ist Overhead &uuml;brigens eine Begr&uuml;ndung, die h&auml;ufig stimmt.) Falls man es wirklich genau wissen will, sollte man wohl die <a href="http://www.intel.com/content/www/us/en/processors/architectures-software-developer-manuals.html">IA-32 Architectures Software Developer&rsquo;s Manuals</a> lesen. Das sind ja nur 3044 Seiten. </div> </div> <div class="question"> <span class="question">Einstufige Seitentabellen sind deutlich einfacher zu verstehen und zu implementieren. Warum verwendet man sie nicht auf 64 Bit Systemen?</span> <div class="answer">Sie w&uuml;rden zu viel Speicher ben&ouml;tigen. Es wird eine Seitentabelle pro Prozess ben&ouml;tigt. Die Gr&ouml;&szlig;e einer einstufigen Seitentabelle berechnet sich wie folgt: Sei `$m$` die Gr&ouml;&szlig;e des Hauptspeichers in Byte, `$p$` die Gr&ouml;&szlig;e einer Seite in Byte und `$a$` die Anzahl der zus&auml;tzlichen Bit pro Seite (Access Control bits, validity. Siehe <a href="http://unix.stackexchange.com/q/68148/4784">StackExchange</a>). Dann gilt: Gr&ouml;&szlig;e der Seitentabelle = Gr&ouml;&szlig;e eines Seiteneintrages &middot; Anzahl der Seiten `$= \lceil \frac{\log_2(\frac{m}{p}) + a}{8}\rceil \text{Byte} \cdot \frac{2^{64} \text{ Byte}}{p \text{ Byte}}$` Typischerweise gilt: `$m = 4 GB = 4 \cdot 2^{30} \text{ Byte} = 2^{32} \text{ Byte}$`, `$p = 4096 \text{ Byte}$` und `$a = 8$`. Daraus folgt eine Seitengr&ouml;&szlig;e von 4 Byte und 4.503.599.627.370.496 Seiten. Das ergibt eine Seitentabellengr&ouml;&szlig;e von 16 Petabyte. </div> </div> <div class="question"> <span class="question">Wenn man nur Segmentierung nutzt, wie kommt man dann von der logischen Adresse auf die physische?</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/segmentation-logical-to-linear-address-300x176.png"><img src="../images/2013/03/segmentation-logical-to-linear-address-300x176.png" alt="Segmentation: Logical to linear address" width="" height="" class="size-medium wp-image-61751" /></a><p class="wp-caption-text">Segmentation: Logical to linear address (<a href="http://download.intel.com/products/processor/manual/325462.pdf">source</a>)</p></div> </div> </div> <div class="question"> <span class="question">Wie ist ein Inode aufgebaut?</span> <div class="answer"> <div style="width: 266px" class="wp-caption aligncenter"><a href="../images/2013/03/inode-struktur-256x300.png"><img src="../images/2013/03/inode-struktur-256x300.png" alt="Struktur eines Inodes" width="" height="" class="size-medium wp-image-61871" /></a><p class="wp-caption-text">Struktur eines Inodes</p></div> </div> </div> <div class="question"> <span class="question">Wie gro&szlig; kann eine Datei maximal werden, wenn man Inodes mit jeweils einem indirekten, doppelt indirektem und dreifach indirektem Block hat?</span> <div class="answer"> Sei `$b$` die Gr&ouml;&szlig;e eines Blocks in Byte und ein Zeiger belege 4 Byte. Dann berechnet sich die maximale Dateigr&ouml;&szlig;e in Byte wie folgt: `$12 \cdot b + \frac{b}{4} \cdot b+ \frac{\frac{b}{4} \cdot b}{4} \cdot b + \frac{\frac{\frac{b}{4} \cdot b}{4} \cdot b}{4} \cdot b = 12 \cdot b + \frac{b^2}{4} + \frac{b^3}{16} + \frac{b^4}{64}$` Bei einer Blockgr&ouml;&szlig;e von 1024 Byte sind das 17,25 GB (<a href="http://www.wolframalpha.com/input/?i=12*1024%2B1024%5E2%2F4%2B1024%5E3%2F16%2B1024%5E4%2F64+byte">Rechnung</a>), bei einer Blockgr&ouml;&szlig;e von 4096 Byte sogar 4,40 TB (<a href="http://www.wolframalpha.com/input/?i=12*4096%2B4096%5E2%2F4%2B4096%5E3%2F16%2B4096%5E4%2F64+byte">Rechnung</a>)! Wenn ihr Linux habt, k&ouml;nnt ihr diese Werte so herausfinden: <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc08 ~ <span class="sb">`</span><span class="nv">$ </span>df Filesystem 1K-blocks Used Available Use% Mounted on /dev/sda1 <span class="m">303869280</span> <span class="m">16418288</span> <span class="m">272015268</span> 6% / udev <span class="m">1889040</span> <span class="m">4</span> <span class="m">1889036</span> 1% /dev tmpfs <span class="m">758712</span> <span class="m">988</span> <span class="m">757724</span> 1% /run none <span class="m">5120</span> <span class="m">0</span> <span class="m">5120</span> 0% /run/lock none <span class="m">1896772</span> <span class="m">772</span> <span class="m">1896000</span> 1% /run/shm none <span class="m">102400</span> <span class="m">8</span> <span class="m">102392</span> 1% /run/user moose@pc08 ~ <span class="nv">$`</span> sudo tune2fs -l /dev/sda1 <span class="p">|</span> grep <span class="s1">&#39;Block size&#39;</span> Block size: 4096</code></pre></div> </div> </div> <div class="question"> <span class="question">Depict the common memory layout of a process. Give an example of the data that is stored in each section.</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/process-memory-layout-300x165.jpg"><img src="../images/2013/03/process-memory-layout-300x165.jpg" alt="Common process memory layout" width="" height="" class="size-medium wp-image-61931" /></a><p class="wp-caption-text">Common process memory layout</p></div> Ich sehe gerade, dass bei rodata wohl das Schl&uuml;sselwort <code>const</code> mit dabei stehen sollte. Statische Variablen k&ouml;nnen nat&uuml;rlich ge&auml;ndert werden. </div> </div> <div class="question"> <span class="question">What is anonymous memory?</span> <div class="answer"> Anonymous memory is memory, that is not backed by a file. Examples are stack and heap. </div> </div> <h2>Material</h2> <p>Material zum Üben (also <a href="http://os.ibds.kit.edu/1556.php">alte Klausuren</a>) gibts wie immer entweder online oder bei der Fachschaft.</p> <p>Die Lösungen zu den Klausuren sind Passwortgeschützt, aber wenn ihr euch einmal über VPN einloggt, stehen ganz unten auf der Seite die Zugangsdaten.</p> <p>Das Skript / die Folien sind im <a href="https://studium.kit.edu/sites/vab/0x8763DF03F4275B4F908D321A58479E61/vorlesungsunterlagen_pwg/Forms/AllItems.aspx?RootFolder=%2fsites%2fvab%2f0x8763DF03F4275B4F908D321A58479E61%2fvorlesungsunterlagen_pwg%2fVorlesung&amp;FolderCTID=&amp;View=%7b2672A6DD-CB1A-408E-888B-441716F3F757%7d">VAB</a>.</p> <p>Folgende Wiki-Artikel und manpages sollte man sich durchlesen:</p> <ul> <li><a href="http://de.wikipedia.org/wiki/Unix-Dateirechte">Unix-Dateirechte</a> und <code>chmod</code> sowie <a href="../linux-access-rights-and-attributes/" title="Linux access rights and attributes">mein Artikel</a>.</li> </ul> <p>Als Buch kann ich neben dem Silberschatz folgendes Empfehlen: LPIC-1 - Vorbereitung auf die Prüfung des Linux Professinal Institute. ISBN 978-3-937514-81-9</p> <h2>Some Random Facts</h2> <ul> <li><code>subl $16, %esp</code> allokiert 16 Byte auf dem Stack.</li> </ul> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: 18.03.2012 um 14:00 Uhr. <strong>Ort</strong>: ich bin im <a href="http://kit.carstengriesheimer.de/map/1459">30.21 Gerthsen</a> (<a href="https://studium.kit.edu/sites/vab/0xC1937D6957186A468FE059ECE05D74B8/Start/homepage.aspx">Hörsaalverteilung</a>) <strong>Dauer</strong>: 60 Minuten <strong>Punkte</strong>: 60 <strong>Benuspunkte</strong>: Abhängig von den Punkten im Übungsschein:</p> <ul> <li>110 - 129 Punkte: 1 Bonuspunkt</li> <li>130 - 149 Punkte: 2 Bonuspunkte</li> <li>150 - 169 Punkte: 3 Bonuspunkte</li> <li>170 - x Punkte: 4 Bonuspunkte</li> </ul> <p><a href="https://studium.kit.edu/sites/vab/0xC1937D6957186A468FE059ECE05D74B8/Vorlesungsunterlagen/BS-WS1213-00aOrga.pdf">Quelle</a> <strong>Nicht vergessen</strong>: Studentenausweis <strong>Einsicht</strong>: 09.04.2013 (war seit spätestens 13.02.2013 bekannt) <strong>Ort der Einsicht</strong>: 07.07 (<a href="https://maps.google.com/maps?q=Vincenz-Prie%C3%9Fnitz-Stra%C3%9Fe+1,+Forschungsstelle+f%C3%BCr+Brandschutztechnik+am+KIT,+Oststadt+76131+Karlsruhe,+Baden-W%C3%BCrttemberg,+Deutschland&amp;hl=de&amp;ie=UTF8&amp;ll=49.012738,8.423853&amp;spn=0.015622,0.042272&amp;geocode=FYXh6wIdLouAAA&amp;hnear=Vincenz-Prie%C3%9Fnitz-Stra%C3%9Fe+1,+Oststadt+76131+Karlsruhe,+Baden-W%C3%BCrttemberg,+Deutschland&amp;t=m&amp;z=15">Vincenz-Priessnitz-Str. 1</a>, 2.OG, links), Raum 215 <strong>Zeit der Einsicht</strong>: Je nach Matrikelnummer unterschiedlich.</p> <h2>Ergebnisse</h2> <strike>H&auml;ngen noch nicht aus (Stand: 15.03.2013)</strike> <p>Hängen nun aus (Stand: 08.04.2013) und <a href="https://studium.kit.edu/sites/vab/0xC1937D6957186A468FE059ECE05D74B8/vorlesungsunterlagen_pwg/Ergebnisse/klausur__18_03_2013.pdf">sind im VAB</a></p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/03/os-klausur-ws201213-ergebnisse-300x227.png"><img src="../images/2013/03/os-klausur-ws201213-ergebnisse-300x227.png" alt="Ergebnisse der OS-Klausur vom WS 2012 / 2013" width="" height="" class="size-medium wp-image-63331" /></a><p class="wp-caption-text">Ergebnisse der OS-Klausur vom WS 2012 / 2013</p></div> How Chrome could be improved - 2nd Post //martin-thoma.com/how-chrome-could-be-improved-2nd-post/ Fri, 22 Feb 2013 09:55:07 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-chrome-could-be-improved-2nd-post <p>Chrome 25 was just released and I would like to mention some features I am still missing. As I already wrote an article <a href="../how-chrome-could-be-improved/">How Chrome could be improved</a> for Chrome 18 I will also mention what was realised meanwhile. If you’re curious if you have the current version, just visit <a href="chrome://chrome/">chrome://chrome/</a>.</p> <h2>Caps lock indicator for password fields</h2> <p>It’s annoying to have caps lock on while typing passwords. So an indicator is needed.</p> <p>I would prefer a caps icon indicator solution:</p> <div style="width: 170px" class="wp-caption alignnone"><a href="../images/2013/02/password-field-caps-icon-indicator.png"><img src="../images/2013/02/password-field-caps-icon-indicator.png" alt="Password field caps icon indicator" width="" height="" class="size-full wp-image-76613" /></a><p class="wp-caption-text">Password field caps icon indicator</p></div> <p>Another way to indicate it would be by text:</p> <div style="width: 246px" class="wp-caption alignnone"><a href="../images/2013/02/password-field-caps-warning.png"><img src="../images/2013/02/password-field-caps-warning.png" alt="Password field caps lock warning" width="" height="" class="size-full wp-image-76614" /></a><p class="wp-caption-text">Password field caps lock warning</p></div> <h2>Improve MathML support</h2> <p>Chrome uses WebKit and WebKit didn’t support MathML for quite a long time. A quite good work-around is <a href="http://www.mathjax.org/">MathJax</a>, but it is a work-around. Native support would be nice. With Chrome 24, they have added MathML support, but its still not optimal:</p> <ul> <li>The font doesn't look very nice (see <a href="http://www.mozilla.org/projects/mathml/demo/texvsmml.html">MathML Torture Test</a> and image below)</li> <li>Multiscripts seems not to work</li> <li>big brackets get a whitespace in the middle (see image below)</li> <li>Scriptlevel seems not to work (see <a href="https://eyeasme.com/Joe/MathML/MathML_browser_test">MathML Browser test</a>)</li> </ul> <p>Here is an image where you can see some of the problems:</p> <div style="width: 631px" class="wp-caption aligncenter"><a href="../images/2013/01/mathml-chrome24-rendering.png"><img src="../images/2013/01/mathml-chrome24-rendering.png" alt="MathML rendered with Chrome 24" width="" height="" class="size-full wp-image-53981" /></a><p class="wp-caption-text">MathML rendered with Chrome 24</p></div> <p>In Chrome 25, MathML was deactivated.</p> <ul> <li><a href="http://caniuse.com/mathml">Which Browsers support MathML?</a></li> <li><a href="http://www.w3.org/Math/XSL/csmall2.xml">Test page</a></li> <li><a href="http://html5test.com/">HTML5test.com</a> - Chrome seems to cheat, MathML is not supported as you can see on the test page. Chrome 25 scores 448/500 Points and 13 bonus points.</li> <li><a href="https://trac.webkit.org/wiki/MathML">Webkit MathML project</a>, <a href="https://bugs.webkit.org/show_bug.cgi?id=3251">Webkit MathML master bug</a></li> </ul> <h2>Stop Animations</h2> <p>Sometimes I would like to be able to stop animations. It can be very useful to be able to stop animations if you want to explain something in the animation. For example, <a href="http://de.wikipedia.org/wiki/Kurvenintegral#Kurvenintegral_erster_Art">this page on Wikipedia</a> has some animations. If you give private lessons in math to another person, you might want to tell something to the single images of the animation. But I am quite sure, that you can’t speak that fast.</p> <p>It would also be nice if you were able to stop all animations on the page. Regrettably, some webmasters carry the usage of animations to excess.</p> <h2>What do I still miss?</h2> <h3>Disable sound for tabs</h3> <p>Sometimes I watch a movie while I play a flash game. Some flash games don’t offer an option to mute them. So I would like to get the possibility to disable sound for one tab.</p> <p>It could look like this.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/disable-tab-sound-300x172.png"><img src="../images/2012/04/disable-tab-sound-300x172.png" alt="Disable the sound of a tab" width="" height="" class="size-medium wp-image-20981" /></a><p class="wp-caption-text">Disable the sound of a tab</p></div> <p>UPDATE: This is <a href="https://code.google.com/p/chromium/issues/detail?id=3541">issue 3541</a>.</p> <h3>Spell checker</h3> <p>I write Blogs in German and in English. So I would like a spell-checker option at the bottom-left corner to switch languages:</p> <div style="width: 708px" class="wp-caption aligncenter"><a href="../images/2012/04/spell-checker.png"><img src="../images/2012/04/spell-checker.png" alt="Spell checker" width="" height="" class="size-full wp-image-21021" /></a><p class="wp-caption-text">Spell checker</p></div> <h3>PDF page numbers</h3> <p>It would be great, if I could see the number of the page your currently on. Sometimes PDF-Documents don’t even have numbers (e.g. LaTeX beamer slides). What do you do if you have a question to one slide if there are dozens of slides? Manually count them, to get the page number you’re looking for?</p> <p><strong>UPDATE</strong>: You actually can jump to any page and share it as links! You only have to add <code>#page=123</code>. For example, you can take a look at this <a href="http://paws.wcu.edu/tsfoguel/tikzpgfmanual.pdf#page231">huge TikZ PDF manual</a>.</p> <p><strong>UPDATE2</strong>: You could automatically adjust this <code>#page=123</code> string according to the page that gets currently viewed. This would make sharing much easier and it would fix the issue that you don’t know where you. Another advantage of this solution is that it doesn’t bloat up the user interface.</p> <p><strong>UPDATE3</strong>: I finally found it! It’s <a href="https://code.google.com/p/chromium/issues/detail?id=66900">issue 66900</a></p> <h3>Security</h3> <h4>Disabling Extensions</h4> <p>Auto-Disable extensions for https. Only PayPal, Amazon, Ebay, GMail and my bank accounts work with https. I don’t need my Addons for these sites and I would appreciate if I could auto-disable them for https.</p> <h4>Password Reuse Visualizer</h4> <p>Firefox offers a tool which helps to identify passwords, that get reused often. It is called ‘<a href="https://addons.mozilla.org/de/firefox/addon/password-reuse-visualizer/">Password Reuse Visualizer</a>’ and looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/password-reuse.png"><img src="../images/2012/04/password-reuse.png" alt="Password Reuse Visualizer" width="" height="" class="size-full wp-image-21101" /></a><p class="wp-caption-text">Password Reuse Visualizer</p></div> <h2>What was realized?</h2> <h3>Rotate PDF</h3> <p>You can view <a href="http://cloud.github.com/downloads/MartinThoma/free-books/01-A-Study-in-Scarlet.pdf">this PDF</a> online as an example. If you make a right-click on it, you can rotate it now.</p> <div style="width: 422px" class="wp-caption aligncenter"><a href="../images/2012/08/pdf-chrome-rightclick-menu.png"><img src="../images/2012/08/pdf-chrome-rightclick-menu.png" alt="Rightclick menu of Google Chrome" width="" height="" class="size-full wp-image-42081" /></a><p class="wp-caption-text">Rightclick menu of Google Chrome</p></div> <h3>HTML5 input elements - partly</h3> <p>Chrome 25 does still not support the <a href="http://www.w3schools.com/html5/html5_form_input_types.asp">datetime input element</a>, tel input element, . They have added a very nice color input element: <input type="color" /> Some Screenshots for non-Chrome users: The button gets displayed like that:</p> <div style="width: 65px" class="wp-caption aligncenter"><a href="../images/2012/08/chrome-color-chooser.png"><img src="../images/2012/08/chrome-color-chooser.png" alt="Google Chrome input type color element" width="" height="" class="size-full wp-image-42051" /></a><p class="wp-caption-text">Google Chrome input type color element</p></div> <p>If you click on it, this dialog box gets displayed:</p> <div style="width: 550px" class="wp-caption aligncenter"><a href="../images/2012/08/chrome-color-dialog.png"><img src="../images/2012/08/chrome-color-dialog.png" alt="Google Chrome Color Dialog Box" width="" height="" class="size-full wp-image-42061" /></a><p class="wp-caption-text">Google Chrome Color Dialog Box</p></div> <p>They have added support to many of the time-elements like week:</p> <div style="width: 472px" class="wp-caption aligncenter"><a href="../images/2013/02/html5-week.png"><img src="../images/2013/02/html5-week.png" alt="HTML5 input type 'week'" width="" height="" class="size-full wp-image-58061" /></a><p class="wp-caption-text">HTML5 input type 'week'</p></div> <p>If you want to check how your browser displays the different input types, here is a <a href="http://www.martin-thoma.de/html5/input.php">test page for input elements</a>.</p> <p>According to</p> <h2>What was realized that I don't need?</h2> <p>The German wiki offers a really nice <a href="http://de.wikipedia.org/wiki/Google_Chrome#Versionsgeschichte">overview of version changes</a>:</p> <ul> <li>Checking spelling mistakes with Google</li> <li>Chrome to mobile</li> <li>Metro-App for Windows 8</li> <li>Support for Retina-Displays</li> <li>Google Cloud Print</li> <li>Improved support for Gamepads</li> </ul> <h3>Web Speech API</h3> <p>Although I think that this feature is very cool, it doesn’t quite work. Here is a <a href="https://www.google.com/intl/en/chrome/demos/speech.html">demo for Web Speech</a>.</p> <p>I said: “Hallo Marie. Die Web Speech API funktioniert nocht nicht so richtig.” (German) which means “Hello Marie. The Web Speech API doesn’t quite work by now.” Web Speech recognized: “Hallo Mausi Mausi. Zieh dich aus.” (German) which means “Hello darling. Undress!”. I guess this would be interesting if I sent it per email without checking the recognized text.</p> How to check if two line segments intersect //martin-thoma.com/how-to-check-if-two-line-segments-intersect/ Thu, 21 Feb 2013 12:19:05 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-check-if-two-line-segments-intersect <p>You have to line segments and you want to know if they intersect. I’ll give you an algorithm how to do it.</p> <h2>Test cases</h2> <p>First of all, we should think about how lines can be arranged:</p> <ul class="gallery mw-gallery-traditional" style="max-width: 652px; width: 652px;"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-t1.png" class="image"><img src="//martin-thoma.com/captions/line-segments-t1.png" alt="T1: One line is horizontal, one vertical and they cross" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase T1</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-t2.png" class="image"><img src="//martin-thoma.com/captions/line-segments-t2.png" alt="T2: An endpoint of one line segment is on the other line segment" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase T2</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-t3.png" class="image"><img src="//martin-thoma.com/captions/line-segments-t3.png" alt="T3: Similar to T4, but with negative coordiantes" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase T3</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-t4.png" class="image"><img src="//martin-thoma.com/captions/line-segments-t4.png" alt="T4: One line is horizontal, one vertical and an end point is on one line" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase T4</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-t5.png" class="image"><img src="//martin-thoma.com/captions/line-segments-t5.png" alt="T5: One line is on the other line" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase T5</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-t6.png" class="image"><img src="//martin-thoma.com/captions/line-segments-t6.png" alt="T6: Line segements are identical" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase T6</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f1.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f1.png" alt="F1: In parallel, close together, one line is completely inside the bounding box of the other line" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F1</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f2.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f2.png" alt="F2: Both lines are parallel." style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F2</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f3.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f3.png" alt="F3: Both lines are horizontal." style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F3</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f4.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f4.png" alt="F4: One line is horizontal, one vertical. They don't cross." style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F4</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f5.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f5.png" alt="F5: Both line segments are on one line, but they don't intersect" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F5</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f6.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f6.png" alt="F6: Both line segments are close together" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F6</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f7.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f7.png" alt="F7: Both lines are horizontal" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F7</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/02/line-segments-f8.png" class="image"><img src="//martin-thoma.com/captions/line-segments-f8.png" alt="F8: Like F6" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Testcase F8</div></div></li></ul> <h2>Bounding boxes</h2> <p>You can draw boxes around line segments such that the edges of the boxes are in parallel to the coordinate axes:</p> <div style="width: 260px" class="wp-caption aligncenter"><a href="../images/2013/02/line-segments-bounding-box-250x300.png"><img src="../images/2013/02/line-segments-bounding-box-250x300.png" alt="Two line segments with their bounding boxes" width="" height="" class="size-medium wp-image-57731" /></a><p class="wp-caption-text">Two line segments with their bounding boxes</p></div> <p>With this image in mind, it is obvious that the bounding boxes need to intersect if the lines should intersect. At this point you have to make a decision: If the endpoint of one line is on the other line, is this an intersection? I think so. If two lines have at least one point in common, they intersect. If two bounding boxes have at least one point in common, they intersect.</p> <p>It is much easier to check if two bounding boxes intersect. It’s simply:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="cm">/**</span> <span class="cm"> * Check if bounding boxes do intersect. If one bounding box</span> <span class="cm"> * touches the other, they do intersect.</span> <span class="cm"> * @param a first bounding box</span> <span class="cm"> * @param b second bounding box</span> <span class="cm"> * @return &lt;code&gt;true&lt;/code&gt; if they intersect,</span> <span class="cm"> * &lt;code&gt;false&lt;/code&gt; otherwise.</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kt">boolean</span> <span class="nf">doBoundingBoxesIntersect</span><span class="o">(</span><span class="n">Point</span><span class="o">[]</span> <span class="n">a</span><span class="o">,</span> <span class="n">Point</span><span class="o">[]</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="n">a</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">x</span> <span class="o">&lt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">x</span> <span class="o">&amp;&amp;</span> <span class="n">a</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">x</span> <span class="o">&gt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">x</span> <span class="o">&amp;&amp;</span> <span class="n">a</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">y</span> <span class="o">&lt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">y</span> <span class="o">&amp;&amp;</span> <span class="n">a</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">y</span> <span class="o">&gt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">y</span><span class="o">;</span> <span class="o">}</span></code></pre></div> <p>If you have difficulties to understand why this works, take a look at this great <a href="http://silentmatt.com/rectangle-intersection/">animation for this formula</a>.</p> <h2>The algorithm</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/02/flowchart.png"><img src="../images/2013/02/flowchart.png" alt="Flowchart how to check if two lines intersect" width="" height="" class="size-full wp-image-57771" /></a><p class="wp-caption-text">Flowchart how to check if two lines intersect</p></div> <p>Looks quite simple, doesn’t it?</p> <h3>Cross product</h3> <p>Well, you might notice that you need to check if one line intersects with a given line segment. To check this, you have to understand one cool idea:</p> <p>You can definie a cross product for points:</p> <p><code> $$\begin{align} \times_P&amp;: Point \times Point \rightarrow \mathbb{R}\\ \times_P(a, b) &amp;:= a.x \cdot b.y - b.x \cdot a.y; \end{align}$$</code></p> <p>This cross product has one nice characteristics:</p> <p><code>$a \times_P b = 0 \Leftrightarrow a$</code> and <code>$b$</code> are on one line through origin</p> <p>You can verify this. If you take two points on a line through origin, they have the same slope <code>$\frac{\Delta y}{\Delta x}$</code>:</p> <p><code> $$ \begin{align} 0 &amp;= a \times_P b\\ \Leftrightarrow 0 &amp;= a.x \cdot b.y - b.x \cdot a.y\\ \Leftrightarrow b.x \cdot a.y &amp;= a.x \cdot b.y\\ \Leftrightarrow \frac{a.y}{a.x} &amp;= \frac{b.y}{b.x} \end{align} $$</code></p> <p>Ok, now you can check if a point is on a line:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** * Checks if a Point is on a line * @param a line (interpreted as line, although given as line * segment) * @param b point * @return &lt;code&gt;true&lt;/code&gt; if point is on line, otherwise * &lt;code&gt;false&lt;/code&gt; */</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">boolean</span> isPointOnLine(LineSegment a, <span style="color:#0a8;font-weight:bold">Point</span> b) { <span style="color:#777">// Move the image, so that a.first is on (0|0)</span> LineSegment aTmp = <span style="color:#080;font-weight:bold">new</span> LineSegment(<span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Point</span>(<span style="color:#00D">0</span>, <span style="color:#00D">0</span>), <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Point</span>( a.second.x - a.first.x, a.second.y - a.first.y)); <span style="color:#0a8;font-weight:bold">Point</span> bTmp = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Point</span>(b.x - a.first.x, b.y - a.first.y); <span style="color:#339;font-weight:bold">double</span> r = crossProduct(aTmp.second, bTmp); <span style="color:#080;font-weight:bold">return</span> <span style="color:#0a8;font-weight:bold">Math</span>.abs(r) &lt; EPSILON; } </pre></div> </div> </div> <p>The second cool characteristic of the cross product is that it can be used to determine if a point b is left or right of the line through the origin and a point a:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** * Checks if a point is right of a line. If the point is on the * line, it is not right of the line. * @param a line segment interpreted as a line * @param b the point * @return &lt;code&gt;true&lt;/code&gt; if the point is right of the line, * &lt;code&gt;false&lt;/code&gt; otherwise */</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">boolean</span> isPointRightOfLine(LineSegment a, <span style="color:#0a8;font-weight:bold">Point</span> b) { <span style="color:#777">// Move the image, so that a.first is on (0|0)</span> LineSegment aTmp = <span style="color:#080;font-weight:bold">new</span> LineSegment(<span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Point</span>(<span style="color:#00D">0</span>, <span style="color:#00D">0</span>), <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Point</span>( a.second.x - a.first.x, a.second.y - a.first.y)); <span style="color:#0a8;font-weight:bold">Point</span> bTmp = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Point</span>(b.x - a.first.x, b.y - a.first.y); <span style="color:#080;font-weight:bold">return</span> crossProduct(aTmp.second, bTmp) &lt; <span style="color:#00D">0</span>; } </pre></div> </div> </div> <p>When we have one line <code>$a$</code> through the origin and one line segment <code>$b$</code>, you can check if <code>$b$</code> crosses <code>$a$</code> by checking if the end points of <code>$b$</code> are on different sides of <code>$a$</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** * Check if line segment first touches or crosses the line that is * defined by line segment second. * * @param first line segment interpreted as line * @param second line segment * @return &lt;code&gt;true&lt;/code&gt; if line segment first touches or * crosses line second, * &lt;code&gt;false&lt;/code&gt; otherwise. */</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">boolean</span> lineSegmentTouchesOrCrossesLine(LineSegment a, LineSegment b) { <span style="color:#080;font-weight:bold">return</span> isPointOnLine(a, b.first) || isPointOnLine(a, b.second) || (isPointRightOfLine(a, b.first) ^ isPointRightOfLine(a, b.second)); } </pre></div> </div> </div> <p>Now you have everything you need:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** * Check if line segments intersect * @param a first line segment * @param b second line segment * @return &lt;code&gt;true&lt;/code&gt; if lines do intersect, * &lt;code&gt;false&lt;/code&gt; otherwise */</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">boolean</span> doLinesIntersect(LineSegment a, LineSegment b) { <span style="color:#0a8;font-weight:bold">Point</span><span style="color:#339;font-weight:bold">[]</span> box1 = a.getBoundingBox(); <span style="color:#0a8;font-weight:bold">Point</span><span style="color:#339;font-weight:bold">[]</span> box2 = b.getBoundingBox(); <span style="color:#080;font-weight:bold">return</span> doBoundingBoxesIntersect(box1, box2) &amp;&amp; lineSegmentTouchesOrCrossesLine(a, b) &amp;&amp; lineSegmentTouchesOrCrossesLine(b, a); } </pre></div> </div> </div> <p>By the way, testcase F5 is the only reason why you need <code>doBoundingBoxesIntersect(box1, box2)</code>. All other tests still pass if you remove this function.</p> <h2>Where do two line segments intersect?</h2> <p>When you know that two line segments intersect, you can also calculate the intersection. The intersection could be a line or only a point.</p> <p>I did this with JavaScript:</p> <iframe src="../html5/line-segment-intersection/" width="800" height="600"> <p>Ihr Browser kann leider keine eingebetteten Frames anzeigen. Die Seite ist <a href="../html5/line-segment-intersection/">hier</a>.</p> </iframe> <p>This is the code that checks for line segments:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** You know that lines a and b have an intersection and now you want to get it! */</span> <span style="color:#080;font-weight:bold">function</span> <span style="color:#06B;font-weight:bold">getIntersection</span>(a, b) { <span style="color:#777">/* the intersection [(x1,y1), (x2, y2)] it might be a line or a single point. If it is a line, then x1 = x2 and y1 = y2. */</span> <span style="color:#080;font-weight:bold">var</span> x1, y1, x2, y2; <span style="color:#080;font-weight:bold">if</span> (a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] == a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]) { <span style="color:#777">// Case (A)</span> <span style="color:#777">// As a is a perfect vertical line, it cannot be represented</span> <span style="color:#777">// nicely in a mathematical way. But we directly know that</span> <span style="color:#777">//</span> x1 = a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; x2 = x1; <span style="color:#080;font-weight:bold">if</span> (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] == b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]) { <span style="color:#777">// Case (AA): all x are the same!</span> <span style="color:#777">// Normalize</span> <span style="color:#080;font-weight:bold">if</span>(a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] &gt; a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>]) { a = {<span style="color:#606"><span style="color:#404">&quot;</span><span>first</span><span style="color:#404">&quot;</span></span>: a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>], <span style="color:#606"><span style="color:#404">&quot;</span><span>second</span><span style="color:#404">&quot;</span></span>: a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>]}; } <span style="color:#080;font-weight:bold">if</span>(b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] &gt; b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>]) { b = {<span style="color:#606"><span style="color:#404">&quot;</span><span>first</span><span style="color:#404">&quot;</span></span>: b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>], <span style="color:#606"><span style="color:#404">&quot;</span><span>second</span><span style="color:#404">&quot;</span></span>: b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>]}; } <span style="color:#080;font-weight:bold">if</span>(a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] &gt; b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>]) { <span style="color:#080;font-weight:bold">var</span> tmp = a; a = b; b = tmp; } <span style="color:#777">// Now we know that the y-value of a[&quot;first&quot;] is the </span> <span style="color:#777">// lowest of all 4 y values</span> <span style="color:#777">// this means, we are either in case (AAA):</span> <span style="color:#777">// a: x--------------x</span> <span style="color:#777">// b: x---------------x</span> <span style="color:#777">// or in case (AAB)</span> <span style="color:#777">// a: x--------------x</span> <span style="color:#777">// b: x-------x</span> <span style="color:#777">// in both cases:</span> <span style="color:#777">// get the relavant y intervall</span> y1 = b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>]; y2 = Math.min(a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>], b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>]); } <span style="color:#080;font-weight:bold">else</span> { <span style="color:#777">// Case (AB)</span> <span style="color:#777">// we can mathematically represent line b as</span> <span style="color:#777">// y = m*x + t &lt;=&gt; t = y - m*x</span> <span style="color:#777">// m = (y1-y2)/(x1-x2)</span> <span style="color:#080;font-weight:bold">var</span> m, t; m = (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>])/ (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] - b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]); t = b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - m*b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; y1 = m*x1 + t; y2 = y1 } } <span style="color:#080;font-weight:bold">else</span> <span style="color:#080;font-weight:bold">if</span> (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] == b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]) { <span style="color:#777">// Case (B)</span> <span style="color:#777">// essentially the same as Case (AB), but with</span> <span style="color:#777">// a and b switched</span> x1 = b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; x2 = x1; <span style="color:#080;font-weight:bold">var</span> tmp = a; a = b; b = tmp; <span style="color:#080;font-weight:bold">var</span> m, t; m = (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>])/ (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] - b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]); t = b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - m*b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; y1 = m*x1 + t; y2 = y1 } <span style="color:#080;font-weight:bold">else</span> { <span style="color:#777">// Case (C)</span> <span style="color:#777">// Both lines can be represented mathematically</span> <span style="color:#080;font-weight:bold">var</span> ma, mb, ta, tb; ma = (a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>])/ (a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] - a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]); mb = (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>])/ (b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] - b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]); ta = a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - ma*a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; tb = b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">y</span><span style="color:#710">&quot;</span></span>] - mb*b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; <span style="color:#080;font-weight:bold">if</span> (ma == mb) { <span style="color:#777">// Case (CA)</span> <span style="color:#777">// both lines are in parallel. As we know that they </span> <span style="color:#777">// intersect, the intersection could be a line</span> <span style="color:#777">// when we rotated this, it would be the same situation </span> <span style="color:#777">// as in case (AA)</span> <span style="color:#777">// Normalize</span> <span style="color:#080;font-weight:bold">if</span>(a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] &gt; a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]) { a = {<span style="color:#606"><span style="color:#404">&quot;</span><span>first</span><span style="color:#404">&quot;</span></span>: a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>], <span style="color:#606"><span style="color:#404">&quot;</span><span>second</span><span style="color:#404">&quot;</span></span>: a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>]}; } <span style="color:#080;font-weight:bold">if</span>(b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] &gt; b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]) { b = {<span style="color:#606"><span style="color:#404">&quot;</span><span>first</span><span style="color:#404">&quot;</span></span>: b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>], <span style="color:#606"><span style="color:#404">&quot;</span><span>second</span><span style="color:#404">&quot;</span></span>: b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>]}; } <span style="color:#080;font-weight:bold">if</span>(a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>] &gt; b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]) { <span style="color:#080;font-weight:bold">var</span> tmp = a; a = b; b = tmp; } <span style="color:#777">// get the relavant x intervall</span> x1 = b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">first</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]; x2 = Math.min(a[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>], b[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">second</span><span style="color:#710">&quot;</span></span>][<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x</span><span style="color:#710">&quot;</span></span>]); y1 = ma*x1+ta; y2 = ma*x2+ta; } <span style="color:#080;font-weight:bold">else</span> { <span style="color:#777">// Case (CB): only a point as intersection:</span> <span style="color:#777">// y = ma*x+ta</span> <span style="color:#777">// y = mb*x+tb</span> <span style="color:#777">// ma*x + ta = mb*x + tb</span> <span style="color:#777">// (ma-mb)*x = tb - ta</span> <span style="color:#777">// x = (tb - ta)/(ma-mb)</span> x1 = (tb-ta)/(ma-mb); y1 = ma*x1+ta; x2 = x1; y2 = y1; } } <span style="color:#080;font-weight:bold">return</span> {<span style="color:#606"><span style="color:#404">&quot;</span><span>first</span><span style="color:#404">&quot;</span></span>: {<span style="color:#606"><span style="color:#404">&quot;</span><span>x</span><span style="color:#404">&quot;</span></span>:x1, <span style="color:#606"><span style="color:#404">&quot;</span><span>y</span><span style="color:#404">&quot;</span></span>:y1}, <span style="color:#606"><span style="color:#404">&quot;</span><span>second</span><span style="color:#404">&quot;</span></span>: {<span style="color:#606"><span style="color:#404">&quot;</span><span>x</span><span style="color:#404">&quot;</span></span>:x2, <span style="color:#606"><span style="color:#404">&quot;</span><span>y</span><span style="color:#404">&quot;</span></span>:y2}}; } </pre></div> </div> </div> <h2>TL;DR</h2> <p>The complete, tested code is on <a href="https://github.com/MartinThoma/algorithms/tree/master/crossingLineCheck/Geometry/src">GitHub</a>. Here is the most important part:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">Geometry</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kd">final</span> <span class="kt">double</span> <span class="n">EPSILON</span> <span class="o">=</span> <span class="mf">0.000001</span><span class="o">;</span> <span class="cm">/**</span> <span class="cm"> * Calculate the cross product of two points.</span> <span class="cm"> * @param a first point</span> <span class="cm"> * @param b second point</span> <span class="cm"> * @return the value of the cross product</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">double</span> <span class="nf">crossProduct</span><span class="o">(</span><span class="n">Point</span> <span class="n">a</span><span class="o">,</span> <span class="n">Point</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="n">a</span><span class="o">.</span><span class="na">x</span> <span class="o">*</span> <span class="n">b</span><span class="o">.</span><span class="na">y</span> <span class="o">-</span> <span class="n">b</span><span class="o">.</span><span class="na">x</span> <span class="o">*</span> <span class="n">a</span><span class="o">.</span><span class="na">y</span><span class="o">;</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Check if bounding boxes do intersect. If one bounding box</span> <span class="cm"> * touches the other, they do intersect.</span> <span class="cm"> * @param a first bounding box</span> <span class="cm"> * @param b second bounding box</span> <span class="cm"> * @return &lt;code&gt;true&lt;/code&gt; if they intersect,</span> <span class="cm"> * &lt;code&gt;false&lt;/code&gt; otherwise.</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">boolean</span> <span class="nf">doBoundingBoxesIntersect</span><span class="o">(</span><span class="n">Point</span><span class="o">[]</span> <span class="n">a</span><span class="o">,</span> <span class="n">Point</span><span class="o">[]</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="n">a</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">x</span> <span class="o">&lt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">x</span> <span class="o">&amp;&amp;</span> <span class="n">a</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">x</span> <span class="o">&gt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">x</span> <span class="o">&amp;&amp;</span> <span class="n">a</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">y</span> <span class="o">&lt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">y</span> <span class="o">&amp;&amp;</span> <span class="n">a</span><span class="o">[</span><span class="mi">1</span><span class="o">].</span><span class="na">y</span> <span class="o">&gt;=</span> <span class="n">b</span><span class="o">[</span><span class="mi">0</span><span class="o">].</span><span class="na">y</span><span class="o">;</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Checks if a Point is on a line</span> <span class="cm"> * @param a line (interpreted as line, although given as line</span> <span class="cm"> * segment)</span> <span class="cm"> * @param b point</span> <span class="cm"> * @return &lt;code&gt;true&lt;/code&gt; if point is on line, otherwise</span> <span class="cm"> * &lt;code&gt;false&lt;/code&gt;</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">boolean</span> <span class="nf">isPointOnLine</span><span class="o">(</span><span class="n">LineSegment</span> <span class="n">a</span><span class="o">,</span> <span class="n">Point</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="c1">// Move the image, so that a.first is on (0|0)</span> <span class="n">LineSegment</span> <span class="n">aTmp</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">LineSegment</span><span class="o">(</span><span class="k">new</span> <span class="nf">Point</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">),</span> <span class="k">new</span> <span class="nf">Point</span><span class="o">(</span> <span class="n">a</span><span class="o">.</span><span class="na">second</span><span class="o">.</span><span class="na">x</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">x</span><span class="o">,</span> <span class="n">a</span><span class="o">.</span><span class="na">second</span><span class="o">.</span><span class="na">y</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">y</span><span class="o">));</span> <span class="n">Point</span> <span class="n">bTmp</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Point</span><span class="o">(</span><span class="n">b</span><span class="o">.</span><span class="na">x</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">x</span><span class="o">,</span> <span class="n">b</span><span class="o">.</span><span class="na">y</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">y</span><span class="o">);</span> <span class="kt">double</span> <span class="n">r</span> <span class="o">=</span> <span class="n">crossProduct</span><span class="o">(</span><span class="n">aTmp</span><span class="o">.</span><span class="na">second</span><span class="o">,</span> <span class="n">bTmp</span><span class="o">);</span> <span class="k">return</span> <span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">r</span><span class="o">)</span> <span class="o">&lt;</span> <span class="n">EPSILON</span><span class="o">;</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Checks if a point is right of a line. If the point is on the</span> <span class="cm"> * line, it is not right of the line.</span> <span class="cm"> * @param a line segment interpreted as a line</span> <span class="cm"> * @param b the point</span> <span class="cm"> * @return &lt;code&gt;true&lt;/code&gt; if the point is right of the line,</span> <span class="cm"> * &lt;code&gt;false&lt;/code&gt; otherwise</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">boolean</span> <span class="nf">isPointRightOfLine</span><span class="o">(</span><span class="n">LineSegment</span> <span class="n">a</span><span class="o">,</span> <span class="n">Point</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="c1">// Move the image, so that a.first is on (0|0)</span> <span class="n">LineSegment</span> <span class="n">aTmp</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">LineSegment</span><span class="o">(</span><span class="k">new</span> <span class="nf">Point</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">),</span> <span class="k">new</span> <span class="nf">Point</span><span class="o">(</span> <span class="n">a</span><span class="o">.</span><span class="na">second</span><span class="o">.</span><span class="na">x</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">x</span><span class="o">,</span> <span class="n">a</span><span class="o">.</span><span class="na">second</span><span class="o">.</span><span class="na">y</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">y</span><span class="o">));</span> <span class="n">Point</span> <span class="n">bTmp</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Point</span><span class="o">(</span><span class="n">b</span><span class="o">.</span><span class="na">x</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">x</span><span class="o">,</span> <span class="n">b</span><span class="o">.</span><span class="na">y</span> <span class="o">-</span> <span class="n">a</span><span class="o">.</span><span class="na">first</span><span class="o">.</span><span class="na">y</span><span class="o">);</span> <span class="k">return</span> <span class="nf">crossProduct</span><span class="o">(</span><span class="n">aTmp</span><span class="o">.</span><span class="na">second</span><span class="o">,</span> <span class="n">bTmp</span><span class="o">)</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="o">;</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Check if line segment first touches or crosses the line that is</span> <span class="cm"> * defined by line segment second.</span> <span class="cm"> *</span> <span class="cm"> * @param first line segment interpreted as line</span> <span class="cm"> * @param second line segment</span> <span class="cm"> * @return &lt;code&gt;true&lt;/code&gt; if line segment first touches or</span> <span class="cm"> * crosses line second,</span> <span class="cm"> * &lt;code&gt;false&lt;/code&gt; otherwise.</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">boolean</span> <span class="nf">lineSegmentTouchesOrCrossesLine</span><span class="o">(</span><span class="n">LineSegment</span> <span class="n">a</span><span class="o">,</span> <span class="n">LineSegment</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="nf">isPointOnLine</span><span class="o">(</span><span class="n">a</span><span class="o">,</span> <span class="n">b</span><span class="o">.</span><span class="na">first</span><span class="o">)</span> <span class="o">||</span> <span class="n">isPointOnLine</span><span class="o">(</span><span class="n">a</span><span class="o">,</span> <span class="n">b</span><span class="o">.</span><span class="na">second</span><span class="o">)</span> <span class="o">||</span> <span class="o">(</span><span class="n">isPointRightOfLine</span><span class="o">(</span><span class="n">a</span><span class="o">,</span> <span class="n">b</span><span class="o">.</span><span class="na">first</span><span class="o">)</span> <span class="o">^</span> <span class="n">isPointRightOfLine</span><span class="o">(</span><span class="n">a</span><span class="o">,</span> <span class="n">b</span><span class="o">.</span><span class="na">second</span><span class="o">));</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Check if line segments intersect</span> <span class="cm"> * @param a first line segment</span> <span class="cm"> * @param b second line segment</span> <span class="cm"> * @return &lt;code&gt;true&lt;/code&gt; if lines do intersect,</span> <span class="cm"> * &lt;code&gt;false&lt;/code&gt; otherwise</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">boolean</span> <span class="nf">doLinesIntersect</span><span class="o">(</span><span class="n">LineSegment</span> <span class="n">a</span><span class="o">,</span> <span class="n">LineSegment</span> <span class="n">b</span><span class="o">)</span> <span class="o">{</span> <span class="n">Point</span><span class="o">[]</span> <span class="n">box1</span> <span class="o">=</span> <span class="n">a</span><span class="o">.</span><span class="na">getBoundingBox</span><span class="o">();</span> <span class="n">Point</span><span class="o">[]</span> <span class="n">box2</span> <span class="o">=</span> <span class="n">b</span><span class="o">.</span><span class="na">getBoundingBox</span><span class="o">();</span> <span class="k">return</span> <span class="nf">doBoundingBoxesIntersect</span><span class="o">(</span><span class="n">box1</span><span class="o">,</span> <span class="n">box2</span><span class="o">)</span> <span class="o">&amp;&amp;</span> <span class="n">lineSegmentTouchesOrCrossesLine</span><span class="o">(</span><span class="n">a</span><span class="o">,</span> <span class="n">b</span><span class="o">)</span> <span class="o">&amp;&amp;</span> <span class="n">lineSegmentTouchesOrCrossesLine</span><span class="o">(</span><span class="n">b</span><span class="o">,</span> <span class="n">a</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Addendum</h2> <p>Some notes for me:</p> <ul> <li>Writing Tests first is worth the effort. I guess it finally saved me some time and it gives me some confidence that my code works.</li> <li>I should update my system. I'm still using Ubuntu 10.04.4 LTS. Especially, I have Eclipse 3.5.2. This means I could not try <a href="http://www.eclemma.org/">EclEmma</a> to test my code coverage ☹</li> <li>LaTeX is great. I've created all images with LaTeX and it was quite fast after I got the first one. Here is the <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/tikz/line-segments">LaTeX source</a>.</li> </ul> <p>edit: I now have a more modern system. So I was able to use EclEmma, which works fine. And I have 100% branch code coverage for this part of code ☺</p> How to create a digital signature //martin-thoma.com/how-to-create-a-digital-signature/ Sat, 16 Feb 2013 11:34:54 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-create-a-digital-signature <p>At first, you have to write your signature on a white sheet of paper. You might have to make several tries:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/02/signature-tries.jpg"><img src="../images/2013/02/signature-tries.jpg" alt="Some tries for a nice signature" width="" height="" class="size-full wp-image-57241" /></a><p class="wp-caption-text">Some tries for a nice signature</p></div> <p>Then you should scan it in a high quality. Now crop the image to the size you like. I have used <a href="http://www.gimp.org/">GIMP</a> for this task:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/crop-to-selection-300x216.png"><img src="../images/2013/02/crop-to-selection-300x216.png" alt="Crop the image to the correct section with GIMP" width="" height="" class="size-medium wp-image-57251" /></a><p class="wp-caption-text">Crop the image to the correct section with GIMP</p></div> <p>Now you should have an image like this one:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/max-mustermann-cropped-signature-300x60.jpg"><img src="../images/2013/02/max-mustermann-cropped-signature-300x60.jpg" alt="Cropped signature" width="" height="" class="size-medium wp-image-57261" /></a><p class="wp-caption-text">Cropped signature</p></div> <h2>Inkscape</h2> <p>Open it with <a href="http://inkscape.org/download">Inkscape</a>, click on the image go to the menu “Path &gt; Trace Bitmap”:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/inkscape-trace-bitmap-300x244.png"><img src="../images/2013/02/inkscape-trace-bitmap-300x244.png" alt="Trace Bitmap in Inkscape" width="" height="" class="size-medium wp-image-57271" /></a><p class="wp-caption-text">Trace Bitmap in Inkscape</p></div> <p>Now choose “Colors”, check “Remove background” and click on “Update”:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/trace-bitmap-settings-300x216.png"><img src="../images/2013/02/trace-bitmap-settings-300x216.png" alt="Trace Bitmap: Settings" width="" height="" class="size-medium wp-image-57291" /></a><p class="wp-caption-text">Trace Bitmap: Settings</p></div> <p>Close the window and look closely at the image. It should now look like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/traced-bitmap-in-inkscape-300x73.png"><img src="../images/2013/02/traced-bitmap-in-inkscape-300x73.png" alt="Traced bitmap in Inkscape" width="" height="" class="size-medium wp-image-57301" /></a><p class="wp-caption-text">Traced bitmap in Inkscape</p></div> <p>You have to click at a part of the image that is currently not selected and then hit the remove key.</p> <p>Now select the “Edit path by nodes” tool:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/edit-path-by-nodes-300x167.png"><img src="../images/2013/02/edit-path-by-nodes-300x167.png" alt="Edit path by nodes" width="" height="" class="size-medium wp-image-57311" /></a><p class="wp-caption-text">Edit path by nodes</p></div> <p>Click on the gray area. The image will look like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/remove-nodes-in-inkscape-300x204.png"><img src="../images/2013/02/remove-nodes-in-inkscape-300x204.png" alt="Remove nodes" width="" height="" class="size-medium wp-image-57321" /></a><p class="wp-caption-text">Remove nodes</p></div> <p>Remove nodes of areas that have to many or where you don’t want to have this gray area. This will take some time.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/inkscape-remove-nodes-300x247.png"><img src="../images/2013/02/inkscape-remove-nodes-300x247.png" alt="Some nodes you should remove" width="" height="" class="size-medium wp-image-57331" /></a><p class="wp-caption-text">Some nodes you should remove</p></div> <p>As soon as you’re finished, you should save your signature as SVG (if you want to edit it later) and as PDF (for LaTeX).</p> <h2>LaTeX</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{pdfpages} % needed for includepdf \begin{document} \section*{Some Text} Lorem ipsum dolor sit amet, pro discere accusam detraxit ei. Ei maluisset definitiones ius. Ut quo persius reprimique, sed ea postulant consulatu, essent tibique et cum. Usu ne etiam facilis, eam everti eruditi ea, his ad eros sententiae. Cu amet admodum recteque mei. Postea aeterno officiis pri in, per te quis numquam, ius ei veri consul. Ei sententiae constituam vix, ad quidam noster bonorum mel. Eu ius rebum disputationi, invenire signiferumque mei ea. Euripidis expetendis argumentum sit eu, viris latine persecuti mel at. Mel ut clita fabellas laboramus, an discere inermis est. Nulla liberavisse usu in. Augue comprehensam ut pro, ne vel dicit oblique. Vel dico omnium et, vis an tota solum argumentum. Eam omnes quidam in. Eu eam illum malorum diceret, nonumes mentitum repudiare eam et.\\ \noindent Yours faithfully\\ \\ \includegraphics[height=10mm]{max-mustermann-cropped-signature.pdf}\\ Max Mustermann \end{document} </pre></div> </div> </div> <h2>Result</h2> <p>The result looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/latex-signed-300x141.png"><img src="../images/2013/02/latex-signed-300x141.png" alt="A signed document, created with LaTeX" width="" height="" class="size-medium wp-image-57351" /></a><p class="wp-caption-text">A signed document, created with LaTeX</p></div> <p>It looks even better if you make the image a little bit darker in the first step with GIMP.</p> CMOS circuits //martin-thoma.com/cmos-circuits/ Fri, 08 Feb 2013 23:39:26 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cmos-circuits <p>CMOS is a technology used to create digital circuits. The basic idea is to combine a pMOS circuit and a nMOS circuit.</p> <h2>MOSFET</h2> <p>Four <abbr title="metal&ndash;oxide&ndash;semiconductor field-effect transistor">MOSFET</abbr> are important for CMOS:</p> <table> <tr> <th>&nbsp;</th> <th>nMOS</th> <th>pMOS</th> </tr> <tr> <th>depletion</th> <td><a href="../images/2013/02/nmos-selbstsleitend.jpg"><img src="../images/2013/02/nmos-selbstsleitend.jpg" alt="nMOS - depletion type" width="222" height="174" class="size-full wp-image-56741" /></a></td> <td><a href="../images/2013/02/pmos-selbstsleitend.jpg"><img src="../images/2013/02/pmos-selbstsleitend.jpg" alt="pMOS depletion" width="215" height="181" class="size-full wp-image-56761" /></a></td> </tr> <tr> <th>enhancement</th> <td><a href="../images/2013/02/nmos-selbstsperrend.jpg"><img src="../images/2013/02/nmos-selbstsperrend.jpg" alt="nMOS - enhancement type" width="221" height="171" class="size-full wp-image-56751" /> <td><a href="../images/2013/02/pmos-selbstsperrend.jpg"><img src="../images/2013/02/pmos-selbstsperrend.jpg" alt="pMOS - enhancement type" width="181" height="163" class="size-full wp-image-56771" /></a></td> <h2>Inverter</h2> <div style="width: 444px" class="wp-caption aligncenter"><a href="../images/2013/02/cmos-inverter.jpg"><img src="../images/2013/02/cmos-inverter.jpg" alt="Inverter in CMOS technology" width="" height="" class="size-full wp-image-56721" /></a><p class="wp-caption-text">Inverter in CMOS technology</p></div> <h2>NAND</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2013/02/cmos-nand.jpg"><img src="../images/2013/02/cmos-nand.jpg" alt="NAND gate in CMOS technology" width="" height="" class="size-full wp-image-56731" /></a><p class="wp-caption-text">NAND gate in CMOS technology</p></div> <h2>Images</h2> I tried to find good software to create those images. I didn't find any that allowed me to create those images. I've tried this: <ul> <li><a href="http://wwwu.uni-klu.ac.at/magostin/cirkuit.html">Cirkuit</a>: Looks good, but crashes.</li> <li>EAGLE: too complex</li> <li>KLogic: seems only to be able to create logic plans</li> <li>PCB Designer: too complex, weird interface</li> </ul> <h2>Anything else?</h2> Which other circuits do we have to know? (Perhaps Transmission Gate?) </a></td></tr></table> Algorithmen II - Klausur //martin-thoma.com/algorithmen-ii-klausur/ Mon, 04 Feb 2013 20:03:14 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/algorithmen-ii-klausur <div class="info">Dieser Artikel beschäftigt sich mit der Vorlesungen des Moduls &bdquo;Algorithmen II&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei Prof. Dr. Wagner gehört.</div> <h2>Vorbereitung</h2> <p><strong>Themen</strong>:</p> <ul> <li>Netzwerke und Fl&uuml;sse <ul> <li>Wert eines Flusses, s-t-Schnitt</li> <li>(Minimale) Schnitte, erhöhende Wege</li> <li>Max-Flow Min-Cut Theorem</li> <li>Ford-Fulkerson-Algorithmus: <ul> <li>Erhöhende Wege, Vorwärts- und R&uuml;ckwärtskanten</li> <li>Spezialfall: Algorithmus von Edmonds und Karp <ul> <li>K&uuml;rzeste erhöhende Wege</li> <li>Laufzeit: `$\mathcal{O}(|V| \cdot |E^2|)$`</li> </ul> </li> </ul> <li>Flussproblem als Lineares Programm</li> <li>Dualität</li> <li>Algorithmus von Goldberg und Tarjan (Residualgraph, Push/Relabel)</li> <li>MINCOSTFLOW, erhöhende Kreise</li> <li>Cycle Canceling Algorithmus</li> <li>Algorithmus von Stoer &amp; Wagner</li> </li> <li>Kreise <ul> <li>Definition: Kreis, einfacher Kreis</li> <li>Kreisbasen, Kreisraum</li> <li>Matroide</li> <li>Zertifikat fur MCB</li> </ul> </li> <li>Randomisierte Algorithmen <ul> <li>Las Vegas Algorithmus / Monte Carlo Algorithmus</li> <li>Monte Carlo Algorithmus f&uuml;r MinCut</li> <li>Fast Random MinCut</li> <li>Maximum Satisfiability Problem</li> <li>Random MaxCut</li> <li>Maximum Satisfiability Problem</li> <li><abbr title="Integer Quadratic Program">IQP</abbr></li> </ul> </li> <li>Algorithmische Geometrie <ul> <li>Was ist ein einfaches Polygon, was ein konvexes Polygon?</li> <li>Sweep Line Algorithmus</li> <li>Konvexe H&uuml;lle: <ul> <li>Graham Scan</li> <li>Gift Wrapping Algorithmus (Jarvis March) &rarr; <a href="http://codegolf.stackexchange.com/q/11035/5240">Code Golf</a></li> </ul> </li> <li>String-Matching <ul> <li>Rabin &amp; Karp</li> <li>Endlichen Automaten</li> <li>Vorberechnungen f&uuml;r viele Suchanfragen: <ul> <li>Suffixbäume</li> <li>Suffixarray</li> <li><abbr title="longest common prefix">LCP</abbr>-Array</li> </ul> </li> </ul> </li> <li>Approximierende Algorithmen <ul> <li>Multiprozessor-Scheduling <ul> <li>List Scheduling Algorithm</li> </ul> </li> <li>Bin Packing <ul> <li><span class="smallCaps">Next Fit</span> Algorithm</li> <li><span class="smallCaps">First Fit</span> Algorithm</li> <li><abbr title="Asymptotic PAS">APAS</abbr></li> <li>Restricted Bin Packing</li> <li>APAS und FAPAS</li> </ul> </li> <li><abbr title="Polynomielles Approximationsschema">PAS</abbr></li> <li><abbr title="Fully Polynomial Approximation Scheme">FPAS</abbr></li> </ul> </li> <li>Parametrisierte Algorithmen &rarr; <a href="http://de.wikipedia.org/wiki/Parametrisierter_Algorithmus">Wiki</a> <ul> <li>Fixed Parameter Tractable</li> <li>Kernbildung (Vertex Cover)</li> <li>Tiefenbeschrankte Suchbäume</li> </ul> </li> <li>Online Algorithmen <ul> <li>Job Scheudling</li> <li>c-kompetitivität</li> <li>Ski-Verleih Beispiel</li> <li>Paging (<abbr title="Longest Forward Distance">LFD</abbr>, Kompetitive Paging-Algorithmen, <span class="hint" title="FIFO, LRU">Konservative Paging-Algorithmen</span>, <a href="http://de.wikipedia.org/wiki/FIFO-Anomalie">B&eacute;l&aacute;dys Anomalie</a>)</li> </ul> </li> <li>Parallele Algorithmen <ul> <li><abbr title="Parallel Random Access Machine">PRAM</abbr> Modell</li> <li>Berechnung von Summen</li> <li>Präfxsumme</li> <li>List Ranking</li> <li>Binaroperationen einer partitionierten Menge</li> <li>Zusammenhangskomponenten</li> <li>Minimaler Spannbaum</li> </ul> </li> <li>Algorithmen fur externen Speicher <ul> <li>Einfaches Rechnermodell</li> <li>Interner Stack / Externer Stack / Externe Warteschlange</li> <li>Multiway Merge Sort</li> <li>Tournament-Bäume</li> </ul> </li> </ul> <h2>Algorithmen und Laufzeiten</h2> <table> <thead> <tr> <th>Algorithmus</th><th>Laufzeit</th> </tr> </thead> <tbody> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung2.pdf#page=18">Algorithmus von Ford und Fulkerson </a></td><td>-</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung2.pdf#page=21">Algorithmus von Edmonds und Karp </a></td><td>`$\mathcal{O}(|V| \cdot |E|^2)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung3.pdf#page=23">Algorithmus von Stoer und Wagner</a></td><td>`$\mathcal{O}(|V|^3)$` oder besser, je nach Wahl des aktiven Knotens</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung5.pdf#page=7">Algorithmus von Stoer und Wagner</a></td><td>`$\mathcal{O}(|V|^2 \log |V| + |V| |E|)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung7.pdf#page=12">Algorithmus von Horton</a></td><td>`$\mathcal{O}(|E|^3 |V|)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung7.pdf#page=14">Algorithmus von de Pina</a></td><td>`$\mathcal{O}(|E|^3 + |E| |V|^2 \log |V|)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung10.pdf#page=27">Sweep-Line-Algorithmus</a></td><td>`$\mathcal{O}(n \cdot \log n)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung11.pdf#page=22">Graham-Scan</a></td><td>`$\mathcal{O}(n \cdot \log n)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung11.pdf#page=22">Gift-Wrapping (Jarvis' March)</a></td><td>`$\mathcal{O}(h \cdot n)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung12.pdf#page=23">Algorithmus von Rabin und Karp</a></td><td>`$\mathcal{O}((n-m) \cdot m)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung12.pdf#page=28">String-Matching-Automat</a></td><td>Vorbereitung: `$\mathcal{O}(|\Sigma| \cdot m^3)$`<br />Matching: `$\mathcal{O}(n)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung13.pdf#page=5">Suffix-Bäume</a></td><td>Vorbereitung: `$\mathcal{O}(n^2)$`<br />Matching: `$\mathcal{O}(m \cdot \log |\Sigma|)$`</td></tr> <tr><td><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung13.pdf#page=26">Suffix-Arrays</a></td><td>Vorbereitung: `$\mathcal{O}(n)$`<br />Matching: `$\mathcal{O}(m \cdot \log |n|)$`</td></tr> </tbody> </table> <h2>Komplexitätsklassen</h2> <div class="definition">Die Klasse `$\mathcal{PP}$` (probabilistic polynomial) enthält alle Entscheidungsprobleme `$\Pi$`, f&uuml;r die es einen polynomialen, randomisierten Algorithmus `$A$` gibt, so dass f&uuml;r alle Instanzen `$I$` von `$\Pi$` gilt: `$ \begin{cases} I \in Y_\Pi &amp; Pr[A(I) \text{ ist "Ja"}] \ge \frac{1}{2} \\ I \notin Y_\Pi &amp; Pr[A(I) \text{ ist "Ja"}] \le \frac{1}{2} \end{cases}$` </div> <div class="definition">Die Klasse `$\mathcal{BPP}$` (bounded error PP) enthält alle Entscheidungsprobleme `$\Pi$`, f&uuml;r die es einen polynomialen, randomisierten Algorithmus `$A$` gibt, so dass f&uuml;r alle Instanzen `$I$` von `$\Pi$` gilt: `$ \begin{cases} I \in Y_\Pi &amp; Pr[A(I) \text{ ist "Ja"}] \geq \frac{3}{4} \\ I \notin Y_\Pi &amp; Pr[A(I) \text{ ist "Ja"}] \leq \frac{1}{4} \end{cases}$` </div> <div class="definition">Die Klasse `$\mathcal{RP}$` (randomisiert polynomial) enthält alle Entscheidungsprobleme `$\Pi$`, f&uuml;r die es einen polynomialen, randomisierten Algorithmus `$A$` gibt, so dass f&uuml;r alle Instanzen `$I$` von `$\Pi$` gilt: `$ \begin{cases} I \in Y_\Pi &amp; Pr[A(I) \text{ ist "Ja"}] \geq \frac{1}{2} \\ I \notin Y_\Pi &amp; Pr[A(I) \text{ ist "Ja"}] = 0 \end{cases}$` </div> Es gilt: `$\mathcal{RP} \subseteq \mathcal{BPP} \subseteq \mathcal{PP}$` <div class="definition">Die Klasse `$\mathcal{NC}$` (Nick's Class) ist die Klasse der Probleme, die durch einen parallelen Algorithmus `$A$` mit polylogarithmischer Laufzeit und polynomieller Prozessorenzahl gelöst werden können, d.h. `$T_A(n) \in \mathcal{O}((\log n)^k_1)$` mit Konstante `$k_1$` und `$P_A(n) \in \mathcal{O}(n^{k_2})$` mit Konstante `$k_2$`. </div> <div class="definition">Die Klasse `$\mathcal{SC}$` (Steve's Class) ist die Klasse der Probleme, die durch einen sequentiellen Algorithmus mit polylogarithmischem Speicherplatzbedarf und polynomieller Laufzeit gelöst werden können. </div> <h2>Übungsblätter</h2> <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebungsblatt1.pdf">Übungsblatt 1</a>, 06.02.2013: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebung1.pdf">Lösung</a> <ul> <li>Amortisierte Laufzeitanalyse: Buchungsmethode</li> <li>Was ist ein Netzwerk? Was ist ein Fluss? Was sind die Kapazitätsbedingung und die Flusserhaltung?</li> </ul> <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebungsblatt2.pdf">Übungsblatt 2</a>, 13.02.2013: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebung2.pdf">Lösung</a> <ul> <li>Wie bekommt man aus dem maximalen Fluss den minimalen Schnitt mit Push-Relabel?</li> <li>Berechnung eines Matchings mit hilfe eines MAX-FLOW-Algorithmus.</li> <li>Wie benutze ich den Algorithmus von Stoer und Wagner? <ul> <li>Funktioniert f&uuml;r negative Kantengewichte nicht, z.B. Graph mit 3 Knoten und 2 negativen Kanten.</li> </ul> </li> </ul> <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebungsblatt3.pdf">Übungsblatt 3</a>, 20.02.2013: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebung3.pdf">Lösung</a> <ul> <li>Algorithmus von de Pina ausf&uuml;hren (<a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung7.pdf">Vorlesung Nr 7</a>)</li> <li>Einiges zu Kreisbasen</li> <li>Wie bekomme ich mit einem nicht-perfektem M&uuml;nzwurf eine 50%-Wahrscheinlichkeit? &rarr; <a href="http://math.stackexchange.com/q/309003/6876">Antwort</a></li> </ul> <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebungsblatt4.pdf">Übungsblatt 4</a>, 20.02.2013: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebung4.pdf">Lösung</a> <ul> <li>Wie finde ich heraus, ob sich zwei gegebene Strecken schneiden? &rarr; <a href="../how-to-check-if-two-line-segments-intersect/" title="How to check if two line segments intersect">Antwort</a></li> </ul> <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebungsblatt5.pdf">Übungsblatt 5</a>, 22.02.2013: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebung5.pdf">Lösung</a> <ul> <li>Wie berechnet man den Suffix-Baum und das Suffix-Array von mississippi? &rarr; <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/vorlesung13.pdf">Vorlesung Nr 13</a></li> <li>Wie funktioniert der Rabin-Karp-Algorithmus zum String-Matching?</li> <li>Wie erstellt man einen String-Matching-Automaten?</li> </ul> <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebungsblatt6.pdf">Übungsblatt 6</a>, 24.02.2013: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/uebung6.pdf">Lösung</a> <ul> <li>Welcher Algorithmus f&uuml;r <span class="smallCaps">Vertex Cover</span> hat eine Approximationsg&uuml;te von 2?</li> </ul> <h2>Fakten und interessante Fragen</h2> <ul> <li>Algorithmus ist konservativ `$\Rightarrow$` Algorithmus ist k-kompetitiv. (Quelle: <a href="http://ls2-www.cs.uni-dortmund.de/~sieling/online07/material/online.pdf#page=5">Begleitmaterial zur Vorlesung Online-Algorihmen</a>, Uni Dortmund)</li> <li>`$c(S, V \setminus S) := \sum_{(i,j) \in E,\\i \in S, j \in V \setminus S} c(i,j)$`</li> </ul> <div class="question"> <span class="question">Was ist der Worst-Case f&uuml;r <span class="smallCaps">List Scheduling</span> mit `$m$` Maschinen?</span> <div class="answer"> Gegeben seien `$n \cdot (m-1)$` Jobs &agrave; 1 Sekunde und ein Job mit `$n$` Sekunden. Die Gesamtlaufzeit beträgt dann `$2 \cdot n - 1$` Sekunden, die beste Laufzeit ist jedoch `$n$` Sekunden. </div> </div> <div class="question"> <span class="question">Was ist der Worst-Case f&uuml;r <span class="smallCaps">Next Fit</span>?</span> <div class="answer"> `$n$` Elemente mit dem Gewicht `$\frac{1}{2}$` und `$2n$` Elemente mit dem Gewicht `$\frac{1}{2}$` und `$2n$` Elemente mit dem Gewicht `$\frac{1}{2 \cdot n}$`. </div> </div> <h2>Termine und Klausurablauf</h2> <strong>Datum</strong>: Freitag, den 1. März 2013 von 11:00 bis 13:00 (<a href="http://www.informatik.kit.edu/klausuren.php?kid=422.35">Quelle</a>) <strong>Ort</strong>: Tulla-Hörsaal (Siehe <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/0225raumlisten.pdf">Liste</a>) <strong>Dauer</strong>: 2 Stunden <strong>Punkte</strong>: 60 <strong>Bestehensgrenze</strong>: 20 <strong>Übungsschein</strong>: Gibt es nicht. <strong>Bonuspunkte</strong>: Gibt es nicht. <strong>Nicht vergessen</strong>: <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> Der Termin f&uuml;r die Klausureinsicht ist noch nicht bekannt (Stand: 01.03.2013) Seit heute (07.03.2013) sind die Ergebnisse da: <ul> <li><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/klausurid-note.pdf">Ergebnisse</a></li> <li><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2012/algo2/ws1213-1-loesung.pdf">Musterlösung</a></li> <li>Termin der Einsicht ist noch nicht bekannt (Stand: 07.03.2013)<br /> Update vom 09.03.2013: Einsicht ist am Dienstag, den 19. März von 15:00 bis 17:00 Uhr und am Donnerstag, den 4. April von 15:00 bis 17:00 jeweils in Raum 301 im Infobau 50.34</li> </ul> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/02/algorithmen-2-stats-300x190.png"><img src="../images/2013/02/algorithmen-2-stats-300x190.png" alt="Algorithmen II - Ergebnis-Statistik" width="" height="" class="size-medium wp-image-62061" /></a><p class="wp-caption-text">Algorithmen II - Ergebnis-Statistik</p></div> </li></ul></li></ul> What can ArrayList / LinkedList do what List can't? //martin-thoma.com/what-can-arraylist-linkedlist-do-what-list-cant/ Mon, 04 Feb 2013 11:50:45 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-can-arraylist-linkedlist-do-what-list-cant <p>I’ve told my students to write</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">List</span><span class="o">&lt;</span><span class="n">MyClass</span><span class="o">&gt;</span> <span class="n">myList</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">MyClass</span><span class="o">&gt;();</span></code></pre></div> <p>instead of</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">MyClass</span><span class="o">&gt;</span> <span class="n">myList</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">MyClass</span><span class="o">&gt;();</span></code></pre></div> <p>as this allows them to switch to any Class that implements List without having to change more code.</p> <p>This does always make sense, except if you need methods from ArrayList or LinkedList. But which methods does <a href="http://docs.oracle.com/javase/7/docs/api/java/util/ArrayList.html">ArrayList</a> / <a href="http://docs.oracle.com/javase/7/docs/api/java/util/LinkedList.html">LinkedList</a> offer that <a href="http://docs.oracle.com/javase/7/docs/api/java/util/List.html">List</a> doesn’t have?</p> <p>ArrayList has:</p> <ul> <li>Object clone()</li> <li>void ensureCapacity(int minCapacity)</li> <li>void removeRange(int fromIndex, int toIndex)</li> <li>void trimToSize()</li> </ul> <p>LinkedList has:</p> <ul> <li>void addFirst(E e)</li> <li>void addLast(E e)</li> <li>Object clone()</li> <li>Iterator<e> descendingIterator() <li>E getFirst()</li> <li>E getLast()</li> <li>boolean offer(E e)</li> <li>boolean offerFirst(E e)</li> <li>boolean offerLast(E e)</li> <li>E peek()</li> <li>E peekFirst()</li> <li>E peekLast()</li> <li>E poll()</li> <li>E pollFirst()</li> <li>E pollLast()</li> <li>E pop()</li> <li>void push(E e)</li> <li>E removeFirst()</li> <li>boolean removeFirstOccurrence(Object o)</li> <li>E removeLast()</li> <li>boolean removeLastOccurrence(Object o)</li> </e></li></ul> Basic Multithreading in Java //martin-thoma.com/basic-multithreading-in-java/ Mon, 04 Feb 2013 00:44:11 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/basic-multithreading-in-java <p>A lot of computing power is wasted in many programs as most programs use only one core. If your program is computation intensive, you might want to put some extra effort in your program and make use of this wasted computing power.</p> <p>There are two ways to execute your code on multiple cores: Multiprocessing and multithreading. Both, processes and threads, provide the possibility to execute code sequences independently and concurrently. But where is the difference?</p> <ul> <li>When you execute code in <strong>multiple processes</strong>, the operating system handles the scheduling. It decides when which process gets executed and tries to find an optimal order. Every process has its own memory segment. A process is sometimes also called "kernel level thread".</li> <li>When you execute code in <strong>multiple threads</strong>, all threads have one process they belong to (see <a href="http://eliezerciriaco.blogspot.de/2009/07/multi-threading-models.html">Multi-Threading models</a>, also from <a href="http://docs.oracle.com/cd/E19455-01/806-3461/6jck06gqk/index.html">Java</a>). Every set of threads that have the same process share their memory.</li> </ul> <p>In Java, you will use multithreading most of the time. I will only write about multithreading, but you can create multiple processes wiht <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/ProcessBuilder.html">ProcessBuilder</a>.</p> <h2>Java Basics for Multithreading</h2> <p>All important lessons you need to learn are covered in <a href="http://docs.oracle.com/javase/tutorial/essential/concurrency/">Java Concurrency Tutorial</a>. If you’re really interested in multithreading, you should read this.</p> <p>You can put the part that can get executed concurrently in a separate class that implements the interface <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Runnable.html">Runnable</a>. This class has a method called run(). You can create a new <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Thread.html#Thread(java.lang.Runnable)">Thread(Runnable)</a> by calling <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Thread.html#start()">start()</a>.</p> <p>Here is an example:</p> <h2>Sum</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">Sum</span> <span class="kd">implements</span> <span class="n">Runnable</span> <span class="o">{</span> <span class="kd">private</span> <span class="kd">final</span> <span class="kt">int</span> <span class="n">UpperEnd</span><span class="o">;</span> <span class="kd">public</span> <span class="nf">Sum</span><span class="o">(</span><span class="kt">int</span> <span class="n">upperEnd</span><span class="o">)</span> <span class="o">{</span> <span class="n">UpperEnd</span> <span class="o">=</span> <span class="n">upperEnd</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">run</span><span class="o">()</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">UpperEnd</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="n">RaceCondition</span><span class="o">.</span><span class="na">bigSum</span><span class="o">++;</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Main</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Main</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">int</span> <span class="n">BIG_NR</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">int</span> <span class="n">NR_THREADS</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">long</span> <span class="n">bigSum</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">args</span><span class="o">.</span><span class="na">length</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;You should specify the number &quot;</span> <span class="o">+</span> <span class="s">&quot;of threads and BIG_NR. Call me like this:\n&quot;</span> <span class="o">+</span> <span class="s">&quot;java -jar RaceCondition.jar 5 20000\n&quot;</span> <span class="o">+</span> <span class="s">&quot;This will create 5 Threads which try to count&quot;</span> <span class="o">+</span> <span class="s">&quot;up to 2000000.\n&quot;</span> <span class="o">+</span> <span class="s">&quot;-v will show status &quot;</span> <span class="o">+</span> <span class="s">&quot;information &quot;</span><span class="o">);</span> <span class="k">return</span><span class="o">;</span> <span class="o">}</span> <span class="kt">boolean</span> <span class="n">verbose</span> <span class="o">=</span> <span class="kc">false</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">args</span><span class="o">.</span><span class="na">length</span> <span class="o">&gt;</span> <span class="mi">2</span><span class="o">)</span> <span class="o">{</span> <span class="n">verbose</span> <span class="o">=</span> <span class="kc">true</span><span class="o">;</span> <span class="o">}</span> <span class="n">NR_THREADS</span> <span class="o">=</span> <span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">args</span><span class="o">[</span><span class="mi">0</span><span class="o">]);</span> <span class="n">BIG_NR</span> <span class="o">=</span> <span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">args</span><span class="o">[</span><span class="mi">1</span><span class="o">]);</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">Thread</span><span class="o">&gt;</span> <span class="n">threads</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Thread</span><span class="o">&gt;();</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">NR_THREADS</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="n">Runnable</span> <span class="n">task</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Sum</span><span class="o">(</span><span class="n">BIG_NR</span><span class="o">);</span> <span class="n">Thread</span> <span class="n">worker</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Thread</span><span class="o">(</span><span class="n">task</span><span class="o">);</span> <span class="n">worker</span><span class="o">.</span><span class="na">start</span><span class="o">();</span> <span class="n">threads</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">worker</span><span class="o">);</span> <span class="o">}</span> <span class="kt">int</span> <span class="n">running</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="k">do</span> <span class="o">{</span> <span class="n">running</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="n">Thread</span> <span class="n">thread</span> <span class="o">:</span> <span class="n">threads</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">thread</span><span class="o">.</span><span class="na">isAlive</span><span class="o">())</span> <span class="o">{</span> <span class="n">running</span><span class="o">++;</span> <span class="o">}</span> <span class="o">}</span> <span class="k">if</span> <span class="o">(</span><span class="n">verbose</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Remaining threads: &quot;</span> <span class="o">+</span> <span class="n">running</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="k">while</span> <span class="o">(</span><span class="n">running</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">RaceCondition</span><span class="o">.</span><span class="na">bigSum</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Call it like this:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">java Main <span class="m">5</span> 2000</code></pre></div> <h2>Race Conditions</h2> <p>When you execute the code above, the output will vary. Why is this the case?</p> <p>In short: The execution order is not defined and <code>RaceCondition.bigSum++</code> is not atomic.</p> <p>Let’s imagine that you call this with two threads only: <code>java Main 2 2000</code></p> <p>Now you could get this execution order:</p> <ul> <li>Thread 1: Loads <code>RaceCondition.bigSum</code>. It is 0.</li> <li>Thread 2: Executes completely. Now <code>RaceCondition.bigSum</code> is 2000</li> <li>Thread 1: Increases the loaded value of <code>RaceCondition.bigSum</code> by 1. Now it is 1.</li> <li>Thread 1: Finishes it's execution. The Value of <code>RaceCondition.bigSum</code> is 2000 = BIG_NR.</li> </ul> <p>Ok, we can obviously get values in <code>$[\text{BIG}\_\text{NR}, \text{NR}\_\text{THREADS} \cdot \text{BIG}\_\text{NR}]$</code>.</p> <p>Can we get smaller values? Yes, we can!</p> <p>Execute:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">java Main <span class="m">50</span> 20000</code></pre></div> <ul> <li>Thread 1 loads <code>bigSum</code>. It's 0.</li> <li>Thread 2 loads <code>bigSum</code>. It's 0.</li> <li>Thread 3 - 50 execute completely.</li> <li>Thread 2 executes until it is at the latest <code>bigSum++</code>. The latest doesn't execute.</li> <li>Thread 1 increases the loaded value from 0 to 1 and writes 1 back</li> <li>Thread 2 loads <code>bigSum</code> = 1</li> <li>Thread 1 executes and finishes.</li> <li>Thread 2 increases the loaded value from 1 to 2 and writes 2 back.</li> </ul> <p>You can get all values in <code>$[2, \text{NR}\_\text{THREADS} \cdot \text{BIG}\_\text{NR}]$</code>!</p> <p>Usually, you don’t want to get different results when you give the same input to your program. How can you fix this? Take a look at <a href="http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/atomic/AtomicLong.html">AtomicLong</a> and replace the <code>long bigNr</code> by the <code>AtomicLong bigNr</code>.</p> <h2>Playing with BASH</h2> <p>If you want to execute this more often, you could save it as a executable JAR and execute the following bash script. It takes three arguments:</p> <ul> <li>`$1: The number of times you execute a the program with a fixed number of THREADS</li> <li>$`2: The maximum number of THREADS you would like to use</li> <li>`$3: BIG_NR</li> </ul> <p>The script executes the program $<code>$1 \cdot </code>$2$` times. The output gets divided by the number of threads and the result is saved in raceCondition.tmp. Every line is one execution of the program. When the second number is BIG_NR, then no race conditions occured.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">rm raceCondition.tmp touch raceCondition.tmp <span class="c"># Up to `$2 threads</span> <span class="k">for</span> <span class="o">((</span> <span class="nv">threads</span><span class="o">=</span>1<span class="p">;</span>threads&lt;<span class="o">=</span><span class="nv">$`</span>2<span class="p">;</span> threads++<span class="o">))</span> <span class="k">do</span> <span class="k">for</span> <span class="o">((</span> <span class="nv">c</span><span class="o">=</span>1<span class="p">;</span> c&lt;<span class="o">=</span><span class="sb">`</span><span class="nv">$1</span><span class="p">;</span> c++ <span class="o">))</span> <span class="k">do</span> <span class="c"># $`threads threads, count up to `$3 in each thread</span> <span class="nv">thisExecutionSum</span><span class="o">=</span><span class="sb">`</span>java -jar RaceCondition.jar <span class="nv">$`</span>threads <span class="sb">`</span><span class="nv">$3</span><span class="sb">`</span> <span class="c"># Normalize: thisExecutionSum / number of threads</span> <span class="nv">normalizedSum</span><span class="o">=</span><span class="sb">`</span>awk -vsome<span class="o">=</span><span class="nv">$`</span>thisExecutionSum -vtotal<span class="o">=</span><span class="sb">`</span><span class="nv">$threads</span> <span class="s1">&#39;BEGIN { printf(&quot;%d\n&quot;, some/total); exit } &#39;</span><span class="sb">`</span> <span class="nb">echo</span> -e <span class="nv">$`</span>threads<span class="s2">&quot;\t&quot;</span><span class="nv">$normalizedSum</span> &gt;&gt; raceCondition.tmp <span class="k">done</span> <span class="k">done</span></code></pre></div> Flipflops und Latches //martin-thoma.com/flipflops-und-latches/ Wed, 30 Jan 2013 13:12:04 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/flipflops-und-latches <p>Flipflops und Latches sind 1-bit Datenspeicher. Es gibt sie als synchrone und als asynchrone Varianten, wobei „synchron“ nur bedeutet, dass das Bauteil zusätzlich einen Takteingang hat. Der wichtigste (und einzige?) Unterschied zwischen Flipflops und Latches ist, dass Flipflops Taktflankengesteuert sind und Latches Pegelgesteuert sind. Das heißt, Flipflops können nur dann ihren Wert ändern, wenn der anliegende Takt von 0 auf 1 wechselt. Latches hingegen können ihren Wert immer ändern, wenn der anliegende Takt auf 1 ist. Beide haben die gleichen Ansteuertabellen, können aber unterschiedliche Zeitdiagramme haben.</p> <p>Interesannt sind vor allem die Ansteuertabellen. Dabei darf man sich nicht von der Art, wie diese aufgeschrieben werden, verwirren lassen: <code>$q^t$</code> ist der Zustand des Flipflops zum Zeitpunkt <code>$t$</code>. Analog dazu ist <code>$q^{t+1}$</code> der Zustand des Flipflops zum Zeitpunkt <code>$t+1$</code>. Nun steht rechts in der Tabelle, welche Signale man braucht um den Zustand <code>$q^{t+1}$</code> zu erreichen, wenn man im Zustand <code>$q^t$</code> ist.</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/01/d-latch.png" class="image"><img src="//martin-thoma.com/captions/d-latch.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">D-Latch</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/01/d-flipflop1.png" class="image"><img src="//martin-thoma.com/captions/d-flipflop1.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">D-Flipflop</div></div></li></ul> <h2>D-Flipflops</h2> <p><abbr title="Delay-Flipflops">D-Flipflops</abbr> ignorieren im Prinzip den aktuellen Zustand und setzt den neuen Zustand einfach auf das d-Signal.</p> <p>D-Flipflops können aus D-Latches erstellt werden:</p> <div style="width: 552px" class="wp-caption aligncenter"><a href="../images/2013/01/d-flipflop.png"><img src="../images/2013/01/d-flipflop.png" alt="D-Flipflop" width="" height="" class="size-full wp-image-55641" /></a><p class="wp-caption-text">D-Flipflop</p></div> <h3>Ansteuertabelle</h3> <table> <tr> <td> <table style="width:auto"> <tr> <th style="border-bottom:1px solid black;">`$q^t$`</th> <th style="border-bottom:1px solid black;border-right: 1px solid black;">`$q^{t+1}$`</th> <th style="border-bottom:1px solid black;">`$d^t$`</th> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">0</td> <td>0</td> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">1</td> <td>1</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">0</td> <td>0</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">1</td> <td>1</td> </tr> </table> </td> <td> <div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2013/01/d-flipflop1-150x150.png"><img src="../images/2013/01/d-flipflop1-150x150.png" alt="D-Flipflop mit Eingang D, unbennanten Takt und Ausgang Q sowie Q negiert." width="" height="" class="size-thumbnail wp-image-55781" /></a><p class="wp-caption-text">D-Flipflop mit Eingang D, unbennanten Takt und Ausgang Q sowie Q negiert.</p></div> </td> </tr> </table> <h2>RS-Flipflops</h2> <p>Das <abbr title="Reset-Set-Flipflop">RS-Flipflop</abbr> bietet zwei Möglichkeiten: Entweder man resettet es, dann wird der neue Zustand 0, oder man setzt es. Dann ist der neue Zustand 1.</p> <p>Ein RS-Flipflop hat zwei Eingänge und einen oder zwei Ausgänge.</p> <h3>Ansteuertabelle</h3> <table> <tr> <td> <table style="width:auto"> <tr> <th style="border-bottom:1px solid black;">`$q^t$`</th> <th style="border-bottom:1px solid black;border-right: 1px solid black;">`$q^{t+1}$`</th> <th style="border-bottom:1px solid black;">`$r^t$`</th> <th style="border-bottom:1px solid black;">`$s^t$`</th> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">0</td> <td>-</td> <td>0</td> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">1</td> <td>0</td> <td>1</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">0</td> <td>1</td> <td>0</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">1</td> <td>0</td> <td>-</td> </tr> </table> </td> <td> <div style="width: 138px" class="wp-caption aligncenter"><a href="../images/2013/01/rs-flipflop.png"><img src="../images/2013/01/rs-flipflop.png" alt="RS-Flipflop" width="" height="" class="size-full wp-image-55631" /></a><p class="wp-caption-text">RS-Flipflop</p></div> </td> </tr> </table> <h2>T-Flipflop</h2> <p><abbr title="Toggle-Flipflop">T-Flipflops</abbr> wechseln den Zustand, wenn T gesetzt ist.</p> <h3>Ansteuertabelle</h3> <table> <tr> <td> <table style="width:auto"> <tr> <th style="border-bottom:1px solid black;">`$q^t$`</th> <th style="border-bottom:1px solid black;border-right: 1px solid black;">`$q^{t+1}$`</th> <th style="border-bottom:1px solid black;">`$T^t$`</th> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">0</td> <td>0</td> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">1</td> <td>1</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">0</td> <td>1</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">1</td> <td>0</td> </tr> </table> </td> <td> <div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2013/01/t-flipflop-150x150.png"><img src="../images/2013/01/t-flipflop-150x150.png" alt="T-Flipflop mit Eingang T, unbenanntem Taktsignal, Ausgang Q und dem negiertem Ausgang Q." width="" height="" class="size-thumbnail wp-image-55831" /></a><p class="wp-caption-text">T-Flipflop mit Eingang T, unbenanntem Taktsignal, Ausgang Q und dem negiertem Ausgang Q.</p></div> </td> <h2>JK-Flipflop</h2> <abbr title="Jump-/Kill-Flipflops">JK-Flipflops</abbr> haben zwei Eing&auml;nge, &bdquo;J&ldquo; und &bdquo;K&ldquo;. Warum die allerdings Jump und Kill genannt werden, ist mir nicht klar. Habt ihr eine Merkregel f&uuml;r die Ansteuertabelle dieses Flipflops? <h3>Ansteuertabelle</h3> <table> <tr> <td> <table style="width:auto"> <tr> <th style="border-bottom:1px solid black;">`$q^t$`</th> <th style="border-bottom:1px solid black;border-right: 1px solid black;">`$q^{t+1}$`</th> <th style="border-bottom:1px solid black;">`$j^t$`</th> <th style="border-bottom:1px solid black;">`$k^t$`</th> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">0</td> <td>0</td> <td>-</td> </tr> <tr> <td>0</td> <td style="border-right: 1px solid black;">1</td> <td>1</td> <td>-</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">0</td> <td>-</td> <td>1</td> </tr> <tr> <td>1</td> <td style="border-right: 1px solid black;">1</td> <td>-</td> <td>0</td> </tr> </table> </td> <td> <div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2013/01/jk-flipflop-150x150.png"><img src="../images/2013/01/jk-flipflop-150x150.png" alt="JK-Flipflop" width="" height="" class="size-thumbnail wp-image-55851" /></a><p class="wp-caption-text">JK-Flipflop</p></div> </td> </tr> </table> </tr></table> Das Consensus-Verfahren //martin-thoma.com/das-consensus-verfahren/ Tue, 29 Jan 2013 16:23:14 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/das-consensus-verfahren <p>Mithilfe des Consensus-Verfahrens können Primimplikanten gefunden werden. Dazu braucht man eine Schaltfunktion <code>$f:\{0,1\}^n \rightarrow \{0,1\}$</code> in disjunktiver Normalform (DNF). Zu betonen ist, dass man keine Minimalform bekommt, da das Überdeckungsproblem noch gelöst werden muss. Dies kann man z.B. mit der <a href="../das-quine-mccluskey-verfahren/" title="Das Quine-McCluskey-Verfahren">zweiten Quineschen Tabelle</a> machen.</p> <p>Dazu baut man eine Tabelle auf. Ich nenne sie mal Consensus-Tabelle. Diese hat 4 Spalten:</p> <ul> <li>Nr.</li> <li>Gebildet aus</li> <li>W&uuml;rfel - eine Spalte f&uuml;r jeden der `$n$` Parameter der Schaltfunktion `$f$`</li> <li>Gestrichen wegen</li> </ul> <p>Nun ergibt jeder Minterm der DNF eine Zeile in der Consensus-Tabelle. Die Reihenfolge ist dabei egal. Die Nr. wird fortlaufend von 1 an gesetzt, die Spalte „Gebildet aus“ bleibt erst mal leer. Nun zieht man eine Linie, um die folgenden Zeilen abzutrennen. Diesen abgetrennten Teil nennen ich nun „Block“.</p> <p>Man vergleicht nun jede Zeile mit den darüber liegenden Zeilen.</p> <ul> <li>*: Falls an einer bestimmten Stelle nur eine der Zeilen ein don't care hat, wird an dieser Stelle der Wert der anderen Zeile genommen. Diese Spalte z&auml;hlt also nicht als unterschiedlich.</li> <li>Unterscheiden sich zwei Zeilen nur an einer Stelle, schreibt man eine neue Zeile in den neuen Block. Diese Zeile hat ein don't care an der Stelle, an der sich die beiden Zeilen unterschieden, eine eigene Nummer. Eventuell &uuml;berdeckt die neue Zeile beide vorhergehenden. Wegen der don't care-Regelung (*) muss das jedoch nicht der Fall sein.</li> </ul> <p>Sobald man alle Zeilen des vorhergehenden Block überprüft hat, kann man wieder eine Linie machen.</p> <p>Das sieht dann etwa so aus (aus Folien von Prof. Dr. Asfour):</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/consensus-verfahren-300x165.png"><img src="../images/2013/01/consensus-verfahren-300x165.png" alt="Consensus-Verfahren" width="" height="" class="size-medium wp-image-55531" /></a><p class="wp-caption-text">Consensus-Verfahren</p></div> <p>Wie man sieht, kann es auch sein, dass eine neue Zeile bereits von einer alten überdeckt wird. Diese Zeilen kann man also direkt streichen. Sobald man keine neuen Zeilen / Blöcke mehr bilden kann, ist man fertig. Die Zeilen, die nicht gestrichen wurden, sind Primimplikanten.</p> <h2>Code</h2> <p>Ich finde Algorithmen werden am eindeutigsten durch Implementierungen beschrieben. Hier ist meine für das Consensus-Verfahren:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">initDatastructure</span><span class="p">(</span><span class="n">terme</span><span class="p">):</span> <span class="n">dictList</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">nr</span><span class="p">,</span> <span class="n">term</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">terme</span><span class="p">):</span> <span class="n">dictList</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&#39;number&#39;</span><span class="p">:</span> <span class="n">nr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="s">&#39;gebildet&#39;</span><span class="p">:</span><span class="s">&#39;&#39;</span><span class="p">,</span> <span class="s">&#39;term&#39;</span><span class="p">:</span><span class="n">term</span><span class="p">,</span> <span class="s">&#39;gestrichen&#39;</span><span class="p">:</span> <span class="bp">False</span><span class="p">})</span> <span class="k">return</span> <span class="n">dictList</span> <span class="sd">&#39;&#39;&#39; check if item1 and item2 differ in at least one digit &#39;&#39;&#39;</span> <span class="k">def</span> <span class="nf">hasComplementaryDigit</span><span class="p">(</span><span class="n">item1</span><span class="p">,</span> <span class="n">item2</span><span class="p">):</span> <span class="n">term1</span> <span class="o">=</span> <span class="n">item1</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]</span> <span class="n">term2</span> <span class="o">=</span> <span class="n">item2</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">term1</span><span class="p">)):</span> <span class="k">if</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="s">&#39;1&#39;</span> <span class="ow">and</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="s">&#39;0&#39;</span><span class="p">)</span> <span class="ow">or</span> \ <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="s">&#39;0&#39;</span> <span class="ow">and</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="s">&#39;1&#39;</span><span class="p">):</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">return</span> <span class="bp">False</span> <span class="sd">&#39;&#39;&#39; check if item1 and item2 have a consensus term &#39;&#39;&#39;</span> <span class="k">def</span> <span class="nf">hasConsensus</span><span class="p">(</span><span class="n">item1</span><span class="p">,</span> <span class="n">item2</span><span class="p">):</span> <span class="n">term1</span> <span class="o">=</span> <span class="n">item1</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]</span> <span class="n">term2</span> <span class="o">=</span> <span class="n">item2</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]</span> <span class="n">differences</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">term1</span><span class="p">)):</span> <span class="k">if</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="ow">and</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&#39;-&#39;</span><span class="p">)</span> <span class="ow">and</span> <span class="p">(</span><span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&#39;-&#39;</span><span class="p">):</span> <span class="n">differences</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">differences</span> <span class="o">&lt;=</span> <span class="mi">1</span> <span class="sd">&#39;&#39;&#39; create the consensus term of two items &#39;&#39;&#39;</span> <span class="k">def</span> <span class="nf">getConsensus</span><span class="p">(</span><span class="n">item1</span><span class="p">,</span> <span class="n">item2</span><span class="p">):</span> <span class="n">term1</span> <span class="o">=</span> <span class="n">item1</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]</span> <span class="n">term2</span> <span class="o">=</span> <span class="n">item2</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]</span> <span class="n">consensus</span> <span class="o">=</span> <span class="s">&#39;&#39;</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">term1</span><span class="p">)):</span> <span class="k">if</span> <span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">]:</span> <span class="n">consensus</span> <span class="o">+=</span> <span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="k">elif</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="ow">and</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&#39;-&#39;</span><span class="p">)</span> <span class="ow">and</span> <span class="p">(</span><span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&#39;-&#39;</span><span class="p">):</span> <span class="n">consensus</span> <span class="o">+=</span> <span class="s">&#39;-&#39;</span> <span class="k">elif</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="ow">and</span> <span class="p">(</span><span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&#39;-&#39;</span><span class="p">):</span> <span class="n">consensus</span> <span class="o">+=</span> <span class="n">term1</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="k">else</span><span class="p">:</span> <span class="n">consensus</span> <span class="o">+=</span> <span class="n">term2</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="k">return</span> <span class="n">consensus</span> <span class="k">def</span> <span class="nf">isIncludedIn</span><span class="p">(</span><span class="n">bigger</span><span class="p">,</span> <span class="n">smaller</span><span class="p">):</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">bigger</span><span class="p">)):</span> <span class="k">if</span> <span class="n">bigger</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="s">&#39;-&#39;</span> <span class="ow">and</span> <span class="n">bigger</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">!=</span> <span class="n">smaller</span><span class="p">[</span><span class="n">i</span><span class="p">]:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">def</span> <span class="nf">consensusIsIncludedIn</span><span class="p">(</span><span class="n">dictList</span><span class="p">,</span> <span class="n">consensus</span><span class="p">):</span> <span class="k">for</span> <span class="n">element</span> <span class="ow">in</span> <span class="n">dictList</span><span class="p">:</span> <span class="k">if</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">==</span> <span class="bp">False</span> <span class="ow">and</span> \ <span class="n">isIncludedIn</span><span class="p">(</span><span class="n">element</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">],</span> <span class="n">consensus</span><span class="p">):</span> <span class="k">return</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;number&#39;</span><span class="p">]</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">def</span> <span class="nf">printList</span><span class="p">(</span><span class="n">dictList</span><span class="p">,</span> <span class="n">horizontalLinesAfter</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&#39;Nr</span><span class="se">\t</span><span class="s"> Gebildet aus </span><span class="se">\t</span><span class="s"> W&amp;uuml;rfel</span><span class="se">\t</span><span class="s"> Gestrichen wegen&#39;</span><span class="p">)</span> <span class="k">for</span> <span class="n">line</span><span class="p">,</span> <span class="n">element</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">dictList</span><span class="p">):</span> <span class="k">if</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">==</span> <span class="bp">False</span><span class="p">:</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="s">&#39;&#39;</span> <span class="k">if</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;number&#39;</span><span class="p">]</span> <span class="o">==</span> <span class="bp">False</span><span class="p">:</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;number&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="s">&#39;&#39;</span> <span class="k">print</span><span class="p">(</span><span class="s">&#39;</span><span class="si">%s</span><span class="se">\t\t</span><span class="si">%s</span><span class="se">\t</span><span class="si">%s</span><span class="se">\t</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">element</span><span class="p">[</span><span class="s">&#39;number&#39;</span><span class="p">],</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gebildet&#39;</span><span class="p">],</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">],</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]))</span> <span class="k">if</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">horizontalLinesAfter</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&#39;-&#39;</span><span class="o">*</span><span class="mi">50</span><span class="p">)</span> <span class="k">def</span> <span class="nf">consensus</span><span class="p">(</span><span class="n">terme</span><span class="p">):</span> <span class="n">dictList</span> <span class="o">=</span> <span class="n">initDatastructure</span><span class="p">(</span><span class="n">terme</span><span class="p">)</span> <span class="n">horizontalLinesAfter</span> <span class="o">=</span> <span class="p">[</span><span class="nb">len</span><span class="p">(</span><span class="n">dictList</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="n">pointer2</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">nextNumber</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">dictList</span><span class="p">)</span> <span class="o">+</span> <span class="mi">1</span> <span class="k">while</span> <span class="n">pointer2</span> <span class="o">!=</span> <span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">dictList</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">pointer2</span> <span class="o">&gt;</span> <span class="n">horizontalLinesAfter</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]:</span> <span class="n">horizontalLinesAfter</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">dictList</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="k">if</span> <span class="n">dictList</span><span class="p">[</span><span class="n">pointer2</span><span class="p">][</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">!=</span> <span class="bp">False</span><span class="p">:</span> <span class="n">pointer2</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">continue</span> <span class="k">for</span> <span class="n">pointer1</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">pointer2</span> <span class="o">-</span> <span class="mi">1</span><span class="p">,</span> <span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">dictList</span><span class="p">[</span><span class="n">pointer1</span><span class="p">][</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">!=</span> <span class="bp">False</span><span class="p">:</span> <span class="k">continue</span> <span class="k">elif</span> <span class="ow">not</span> <span class="n">hasComplementaryDigit</span><span class="p">(</span><span class="n">dictList</span><span class="p">[</span><span class="n">pointer1</span><span class="p">],</span> <span class="n">dictList</span><span class="p">[</span><span class="n">pointer2</span><span class="p">]):</span> <span class="k">continue</span> <span class="k">elif</span> <span class="ow">not</span> <span class="n">hasConsensus</span><span class="p">(</span><span class="n">dictList</span><span class="p">[</span><span class="n">pointer1</span><span class="p">],</span> <span class="n">dictList</span><span class="p">[</span><span class="n">pointer2</span><span class="p">]):</span> <span class="k">continue</span> <span class="n">consensus</span> <span class="o">=</span> <span class="n">getConsensus</span><span class="p">(</span><span class="n">dictList</span><span class="p">[</span><span class="n">pointer1</span><span class="p">],</span> <span class="n">dictList</span><span class="p">[</span><span class="n">pointer2</span><span class="p">])</span> <span class="c"># Wird der neue Konsensus-Term eventuell bereits &amp;uuml;berdeckt?</span> <span class="n">gestrichen</span> <span class="o">=</span> <span class="n">consensusIsIncludedIn</span><span class="p">(</span><span class="n">dictList</span><span class="p">,</span> <span class="n">consensus</span><span class="p">)</span> <span class="k">if</span> <span class="n">gestrichen</span> <span class="o">==</span> <span class="bp">False</span><span class="p">:</span> <span class="n">nr</span> <span class="o">=</span> <span class="n">nextNumber</span> <span class="n">nextNumber</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="n">nr</span> <span class="o">=</span> <span class="bp">False</span> <span class="c"># Kann dank dem neuen Consensus-Term etwas gestrichen werden?</span> <span class="k">if</span> <span class="n">gestrichen</span> <span class="o">==</span> <span class="bp">False</span><span class="p">:</span> <span class="k">for</span> <span class="n">element</span> <span class="ow">in</span> <span class="n">dictList</span><span class="p">:</span> <span class="k">if</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">==</span> <span class="bp">False</span> <span class="ow">and</span> \ <span class="n">isIncludedIn</span><span class="p">(</span><span class="n">consensus</span><span class="p">,</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;term&#39;</span><span class="p">]):</span> <span class="n">element</span><span class="p">[</span><span class="s">&#39;gestrichen&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="n">nr</span> <span class="n">dictList</span><span class="o">.</span><span class="n">append</span><span class="p">({</span><span class="s">&#39;number&#39;</span> <span class="p">:</span> <span class="n">nr</span><span class="p">,</span> <span class="s">&#39;gebildet&#39;</span><span class="p">:</span> <span class="nb">str</span><span class="p">(</span><span class="n">dictList</span><span class="p">[</span><span class="n">pointer2</span><span class="p">][</span><span class="s">&#39;number&#39;</span><span class="p">])</span> <span class="o">+</span> <span class="s">&#39;, &#39;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">dictList</span><span class="p">[</span><span class="n">pointer1</span><span class="p">][</span><span class="s">&#39;number&#39;</span><span class="p">]),</span> <span class="s">&#39;term&#39;</span><span class="p">:</span> <span class="n">consensus</span><span class="p">,</span> <span class="s">&#39;gestrichen&#39;</span> <span class="p">:</span> <span class="n">gestrichen</span><span class="p">})</span> <span class="n">pointer2</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">printList</span><span class="p">(</span><span class="n">dictList</span><span class="p">,</span> <span class="n">horizontalLinesAfter</span><span class="p">)</span> <span class="n">consensus</span><span class="p">([</span><span class="s">&#39;-0-00&#39;</span><span class="p">,</span> <span class="s">&#39;--00-&#39;</span><span class="p">,</span> <span class="s">&#39;-1-00&#39;</span><span class="p">,</span> <span class="s">&#39;010-1&#39;</span><span class="p">,</span> <span class="s">&#39;1-11-&#39;</span><span class="p">,</span> <span class="s">&#39;110-1&#39;</span><span class="p">])</span> <span class="c">#consensus([&#39;-00-&#39;, &#39;-011&#39;, &#39;0100&#39;])</span></code></pre></div> <p>Ausgabe:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">Nr Gebildet aus W&amp;uuml;rfel Gestrichen wegen 1 -0-00 7 2 --00- 3 -1-00 7 4 010-1 9 5 1-11- 6 110-1 9 -------------------------------------------------- 7 3, 1 ---00 8 6, 5 11-11 9 6, 4 -10-1 -------------------------------------------------- 10 7, 5 1-1-0 8, 2 110-1 9 9, 7 -100- 2 9, 5 11-11 8 -------------------------------------------------- 10, 8 1111- 5 10, 2 1--00 7 --------------------------------------------------</code></pre></div> <h2>Quellen</h2> <p>Die Folien von Dr. Asfour (DT-VL12) sowie die Vorlesung (auf <a href="http://www.youtube.com/watch?v=K1NAj4ecPDw#t=31m18s">YouTube</a> verfügbar. Der <a href="http://www.youtube.com/watch?v=K1NAj4ecPDw#t=47m30s">interessante Teil</a> beginnt erst sehr spät.). Es wurde sogar <a href="http://www.youtube.com/watch?v=4X1w0B4w65k#t=1h10m38s">später nochmals von Herrn Prof. Dr. Asfour erklärt</a>.</p> Das Quine-McCluskey-Verfahren //martin-thoma.com/das-quine-mccluskey-verfahren/ Tue, 29 Jan 2013 14:34:06 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/das-quine-mccluskey-verfahren <p>Das Quine-McCluskey-Verfahren wird angewendet, wenn man eine Schaltfunktion minimieren will. Es muss also eine Schaltfunktion gegeben sein. Es sollte eigentlich zusätzlich Kostenfunktion gegeben sein, aber meist ist das nicht der Fall.</p> <h2>Verfahren</h2> <p><strong>Gegeben</strong>: Eine Schaltfunktion <code>$f:\{0,1\}^n \rightarrow \{0,1\}, \; n \in \mathbb{N}$</code> <strong>Schritt 1:</strong> Aufstellen der Funktionstabelle. Sie hat die Spalten</p> <ul> <li>&bdquo;Nr.&ldquo;, die bei 0 beginnt und bis `$2^n - 1$` geht.</li> <li>Eine Spalte pro Funktionsparameter (z.B. `$a, b, c, ...$`)</li> <li>Eine Spalte f&uuml;r den Funktionswert `$f(a,b,c,...)$`</li> </ul> <p><strong>Schritt 2</strong>: Aufstellen der ersten Quinesche Tabelle 0ter Ordnung.</p> <p>Sie hat die Spalten</p> <ul> <li>&bdquo;Nr.&ldquo;</li> <li>Eine Spalte pro Parameter</li> <li>&bdquo;✓&ldquo; (H&auml;kchen)</li> </ul> <p>In der ersten Quineschen Tabelle stehen nur noch die Zeilen, deren Funktionswert 1 ist. Das sind die sogenannten Minterme. Zusätzlich sind sie nach Anzahl der 1er geordnet.</p> <p><strong>Schritt 3</strong>: <code>$i$</code>-tes Zusammenfassen</p> <p>Nun erstellt man die erste Quinesche Tabelle <code>$i$</code>-ter Ordnung. Also beim ersten mal erster Ordnung, beim zweiten Mal zweiter Ordnung, … Diese Tabellen haben alle die gleichen Spalten und die Zeilen-Anzahl kann sowohl wachsen als auch schrumpfen. Das <code>$i$</code> gibt dabei die Anzahl der „don’t care“ Stellen an, also der Stellen die sowohl 0 als auch 1 sein können.</p> <p>Um aus der ersten Quinesche Tabelle <code>$(i-1)$</code>-ter Ordnung die rsten Quinesche Tabelle <code>$i$</code>-ter Ordnung zu erstellen, geht man wie folgt vor:</p> <ul> <li>Vergleiche alle Zeilen, in denen sich die Anzahl der 1er um genau 1 unterscheidet: <ul> <li>Unterscheiden sich Zeile Nr. x und Zeile Nr. y an nur einer Stelle, so schreibe in die Tabelle `$i$`ter Ordnung eine neue Zeile. Die Nummer dieser Zeile ist &bdquo;x, y&ldquo; und sie hat an der Stelle, an der sich die Zeilen x und y unterschieden, ein don't care.</li> <li>Hake die Zeilen x und y in der Tabelle `$(i-1)$`-ter Ordnung ab</li> </ul> </li> </ul> <p>Es ist möglich, das Zeilen nicht abgehakt werden, weil sie sich mit keiner Zeile zusammenfassen lassen. Das ist ok. Sobald in einem Schritt keine Zusammenfassung mehr möglich ist, ist man hier fertig. Falls noch eine Möglich ist, geht man wieder in Schritt 3.</p> <p>Nun schreibt man alle Zeilen auf, die nicht abgehakt sind. Das sind die Primimplikanten.</p> <p><strong>Schritt 4</strong>: Aufstellen der zweiten Quineschen Tabelle</p> <p>Die zweite Quinesche Tabelle (auch Überdeckungstabelle genannt) hat folgende Spalten:</p> <ul> <li>Primimplikanten</li> <li>Eine Spalte pro Minterm. Die Beschriftung ist dabei eine Nr.</li> <li>Eine Spalte &bdquo;Kosten&ldquo;</li> </ul> <p>Nun macht man in den Zellen ein Kreuz, in denen der Primimplikant den Minterm abdeckt (also wenn die Nr. im Namen des Minterms vorkommt). Die Kosten muss man pro Primimplikant berechnen.</p> <p><strong>Schritt 5</strong>: Vereinfachen der zweiten Quineschen Tabelle</p> <p>Dieser Schritt erinnert mich irgendwie an Sudoku.</p> <ul> <li><em>Zeilendominanz</em>: Hat eine Zeile a nur x-e an Stellen, wo auch eine andere Zeile b x-e hat und ist Zeile b nicht teurer als a, so kann Zeile a gestrichen werden. Also: Es wird die Zeile mit weniger x gestrichen</li> <li><em>Spaltendominanz</em>: &Uuml;berdeckt eine Spalte eine andere Spalte mit ihren x-en, so kann die Spalte mit <u>mehr</u> x-en gestrichen werden.</li> </ul> <p><strong>Schritt 6</strong>: Identifizieren von Kernprimimplikanten.</p> <p>Wenn eine Zeile als einzige an einer bestimmten Spalte ein x hat, ist der zugehörige Primimplikant ein Kernprimimplikant. Er muss auf jeden Fall in der Minimalform vorkommen. Diesen schreibt man sich also auf, Streicht die Zeile und alle Spalten, an denen der Kernprimimplikant ein x hatte. Dann geht man zurück zu Schritt 5.</p> <p>Gab es keinen Kernprimimplikanten, geht man zu Schritt 7.</p> <p><strong>Schritt 7</strong>: Handarbeit</p> <p>Ich muss mal nach einem Beispiel suchen, aber ich glaube es ist möglich, dass man die zweite Quinesche Tabelle ab einem gewissen Punkt nicht mehr vereinfachen kann, aber dennoch Zeilen und Spalten übrig sind. Dann muss man „durch scharfes Hinsehen“ (also Brute-Force) die Minimalform finden, oder? Hier bin ich mir nicht ganz sicher.</p> <h2>Beispiele</h2> <p>Die folgende Aufgabe ist vom Übungsblatt 7 (WS 2012/2013). Herr Terlemez hat mir freundlicherweise erlaubt, sie hier verwenden zu dürfen. (Die <a href="http://ti.ira.uka.de/TI-1/Uebungen/Uebungen.php">offiziellen Aufgaben und Lösungen</a> sind passwortgeschützt.)</p> <p><strong>Aufgabe</strong>: Gegeben sei die Schaltfunktion</p> <p><code>$g(d,c,b,a) := dc \bar b a \lor d \bar c ba \lor d \bar c \bar b a \lor \bar d ca \lor dcb$</code></p> <ol> <li>Bestimmen Sie alle Primimplikanten von `$g$` mit Hilfe der 1. Quineschen Tabelle des Quine-McCluskey-Verfahrens.</li> <li>Geben Sie die &Uuml;berdeckungstabelle (2. Quinesche Tabelle) f&uuml;r die gefundenen Primimpikanten an (ohne Vereinfachung). Lesen Sie eine disjunktive Minimalform von `$g$` ab.</li> </ol> <p><strong>Lösung</strong>: (Habe gerade leider keine Zeit, diese abzutippen. Kommt vielleicht noch.)</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/digitaltechnik-aufgabe-7-2-1-300x236.jpg"><img src="../images/2013/01/digitaltechnik-aufgabe-7-2-1-300x236.jpg" alt="Handschriftliche L&ouml;sung der Aufgabe 7.2.1 aus DT" width="" height="" class="size-medium wp-image-56641" /></a><p class="wp-caption-text">Handschriftliche L&ouml;sung der Aufgabe 7.2.1 aus DT</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/digitaltechnik-aufgabe-7-2-2-300x253.jpg"><img src="../images/2013/01/digitaltechnik-aufgabe-7-2-2-300x253.jpg" alt="Handschriftliche L&ouml;sung der Aufgabe 7.2.2 aus DT" width="" height="" class="size-medium wp-image-56651" /></a><p class="wp-caption-text">Handschriftliche L&ouml;sung der Aufgabe 7.2.2 aus DT</p></div> <h2>Quellen</h2> <p>Ich habe diesen Artikel mit meinem Wissen aus den Folien (DT-VL12), der <a href="http://www.youtube.com/watch?v=K1NAj4ecPDw&amp;list=PL025B377F9094FCB9&amp;index=13">Vorlesung</a> und dem Tutorium erstellt.</p> TI-Klausur (DT & RO) //martin-thoma.com/ti-klausur-dt-ro/ Mon, 28 Jan 2013 00:25:14 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ti-klausur-dt-ro <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesungen &bdquo;Digitaltechnik und Entwurfsverfahren&ldquo; sowie &bdquo;Rechnerorganisation&ldquo; des Moduls &bdquo;Technische Informatik&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe die Vorlesungen bei Herrn Prof. Dr. Asfour geh&ouml;rt.</div> <h2>Vorbereitung DT</h2> <p><strong>Themen</strong>:</p> <ul> <li>Zahlensysteme: Horner-Schema, Euklidischer Algorithmus</li> <li>Zahlendarstellungen: Wie wandle ich eine Zahl von 10-er-System ins Zahlensystem xy um und umgekehrt? <ul> <li>Vorzeichen</li> <ul> <li>Betrag-Vorzeichen &rarr; <span class="hint" title="Erstes Bit ist 1, wenn die Zahl negativ ist. Sonst wird die Zahl einfach bin&auml;r dargestellt.">Antwort</span></li> <li>Einer-Komplement &rarr; <span class="hint" title="Betrag der Zahl dual darstellen, bits invertieren">Antwort</span></li> <li>Zweier-Komplement &rarr; <span class="hint" title="Wie Einer-Komplement, 1 addieren">Antwort</span></li> <li>Exzess-q &rarr; <span class="hint" title="Man fasst die durch Exzess-q dargestellte Zahl als Bin&auml;rzahl auf, addiert -q darauf und erh&auml;lt so die dargestellte Zahl">Antwort</span></li> </ul> <li>Komma <ul> <li>Festkomma &rarr; <span class="hint" title="int, long, char">Beispiele</span></li> <li>Gleitkomma &rarr; <span class="hint" title="float, double">Beispiele</span> (`$\pm \text{Mantisse} \cdot b^\text{Exponent}$`)</li> </ul> </li> </ul> </li> <li>IEEE 754 Format <ul> <li><a href="../a-practical-approach-to-floats/">A practical approach to floats</a></li> <li>Wie wird NaN dargestellt? Wie wird `$-\infty$` und `$+\infty$` dargestellt?</li> <li>Was ist eine normalisierte Zahl, was eine denormalisierte?</li> </ul> </li> <li>Was ist <span class="hint" title="Alle Ziffern von 0-9 werden im 2er-System dargestellt.">BCD</span>, <span class="hint" title="Die Ziffern von 0-4 werden im 2er-System dargestellt. Dann geht es bei (B)_16 = 1011 weiter.">AIKEN</span> und <span class="hint" title="+3 auf jede Ziffer, dann wie BCD">STIBITZ</span>? Wie werden die Ziffern von 0 - 9 dort dargestellt?</li> <li>Was sind Hamming-Codes? &rarr; <a href="../error-correcting-codes/">Antwort</a></li> <li>Wie lauten die Huntingtonschen Axiome? &rarr; <a href="../beweise-aus-der-booleschen-algebra/">Antwort</a></li> <li>Nenne 3 verschiedene vollst&auml;ndige Operatorensysteme. &rarr; <span class="hint" title="(UND, ODER, NOT), (NAND), (NOR)">Antwort</span></li> <li>Was sind Primterme, Primimplikanten, Primimplikate, Minterme und Maxterme?</li> <li>Was sind DMF, DNF, KMF, KNF?</li> <li>Wie wende ich die Shannon-Zerlegung an? &rarr; <a href="../wie-wende-ich-die-shannon-zerlegung-an/">Antwort</a></li> <li>Wie minimiere ich Funktionen mit KV-Diagrammen?</li> <li>Wie funktioniert das Quine-McCluskey Verfahren? &rarr; <a href="../das-quine-mccluskey-verfahren/">Antwort</a></li> <li>Was macht das Consensus-Verfahren? &rarr; <a href="../das-consensus-verfahren/">Antwort</a></li> <li>Wie funktioniert das Nelson-Verfahren?</li> <li>Was bedeutet selbstleitend und selbstsperrend?</li> <li>Was ist <abbr title="metal-oxide-semiconductor field-effect transistor">MOSFET</abbr>? &rarr; <a href="http://commons.wikimedia.org/wiki/File:N-Kanal-MOSFET_(Schema).svg">Aufbau</a></li> <li><abbr title="Complementary Metal Oxide Semiconductor">CMOS</abbr>, N-MOS, P-MOS</li> <li>Was ist der Unterschied zwischen einem Hasard und einem Hasard-Fehler?</li> <li>Woran erkennt man Funktionshasards, woran Strukturhasards?</li> <li>Wie lauten die Ansteuertabellen von D-, T-, JK- und RS-Flipflops? &rarr; <a href="../flipflops-und-latches/">Antwort</a></li> <li>Was macht ein Carry-ripple-Addierer? &rarr; <span class="hint" title="Nutzt zur Addition zweier n-Stelliger Zahlen (n-1) Volladdierer und einen Halbaddierer.">Antwort</span></li> <li>Inwiefern stellt der Carry-lookahead-Addierer eine Verbesserung des Carry-ripple-Addierers dar? &rarr; <span class="hint" title="Der Carry-ripple-Addierer rechnet von dem LSB zu dem MSB Schritt f&uuml;r Schritt. Der Carry-Lookahead-Addierer versucht dies zu beschleunigen, indem er die &Uuml;bertr&auml;ge direkt aus den Eingangsvariablen berechnet.">Antwort</span></li> <li>Was macht man, wenn bei der Addition zweier BCD-Zahlen eine Pseudotetrade auftritt? &rarr; <span class="hint" title="6 auf die betroffene Tetrade addieren.">Antwort</span></li> <li>Was macht man, wenn bei der Addition zweier BCD-Zahlen ein &Uuml;bertrag in die n&auml;chste BCD-Ziffer auftritt? &rarr; <span class="hint" title="6 auf die Stelle addieren, die den &Uuml;bertrag auf die n&auml;chste Stelle verursachte.">Antwort</span></li> <li>Was macht man, wenn bei der Addition zweier BCD-Zahlen bei der Korrekturaddition ein &Uuml;bertrag auftrat? &rarr; <span class="hint" title="Nichts.">Antwort</span></li> <li>Was ist die PPS-Methode? &rarr; <span class="hint" title="Eine Multiplikationsmethode (Partial Product sum). Siehe DT-VL21.pdf">Antwort</span></li> </ul> <h2>Vorbereitung RO</h2> <p><strong>Themen</strong>:</p> <ul> <li>Y-Diagramm</li> <li>Aufbau eines Mikroprozessors</li> <li>Umrechnen von Zahlensystemen</li> <li>RAM-Typen (DRAM, FPM-DRAM, EDO-RAM, SDRAM, DDRAM, DDR-SDRAM, RDRAM)</li> <li>Cache-Speicher</li> </ul> <p><strong>Begriffe</strong></p> <ul> <li>Was sind Tristate-Treiber? &rarr; <span class="hint" title="Gatterform, die nicht nur Hi und Lo weiterleiten kann, sondern auch einen dritten, gegen Spannungen beider Polarit&auml;ten, hochohmigen Zustand haben k&ouml;nnen. Dadurch kann z.B. ein Baustein vom Bus abgetrennt werden. Sie dienen zum Abschalten des gleichzeitigen Zugriffs mehrerer Komponenten auf Systembusse.">Antwort</span></li> <li>Was ist der Unterschied zwischen <span class="hint" title="Symbolische Repr&auml;sentation der Maschinensprache, die f&uuml;r den Menschen verst&auml;ndlich und anschaulich ist, z.B. add `$s2, $`s1, `$s0">Assembler</span>, <span class="hint" title="Repr&auml;sentation von Anweisungen, die f&uuml;r einen Mikroprozessor unmittelbar verst&auml;ndlich sind, z.B. 00000000110000100011000000100001">Maschinensprache</span> und Mikrobefehlen?</li> <li>Wof&uuml;r stehen RISC und CISC und was sind Beispiele? &rarr; <span class="hint" title="Reduced Instruction Set Computer (z.B. MIPS), Complex Instruction Set Computer (z.B. x86)">Antwort</span></li> <li>Was ist ein User/System Bit, was ein Trace Bit und was ein Decimal bit? &rarr; <span class="hint" title="Das User/System bit bestimmt, ob sich das System im eingeschr&auml;nkten User-Modus oder im uneingeschr&auml;nktem Systemmodus befindet. Das Trace Bit erlaubt Befehlsabarbeitung im Einzelschritt-Modus zum Debuggen und das Decimal Bit entscheidet, ob Dual oder BCD gerechnet wird.">Antwort</span></li> <li>Welche Informationen k&ouml;nnen im Statusregister des Rechnewerkes stehen? &rarr; <span class="hint" title="Carry, Overflow, Zero, Sign, ...">Antwort</span></li> <li>Welche Informationen k&ouml;nnen im Akkumulator stehen? &rarr; <span class="hint" title="alle ALU Ergebisse">Antwort</span></li> <li>Warum ben&ouml;tigt die ALU Hilfsregister? &rarr; <span class="hint" title="Ohne die Hilfsregister w&uuml;rden w&auml;hrend der ALU-Rechenzeit durch Hasards und Wettl&auml;ufe Schwankungen am Ausgang entstehen.">Antwort</span></li> <li>Entspricht das logische Rechtsschieben der Division durch zwei? &rarr; <span class="hint" title="Nein, da bei negativen Zahlen die 1 im MSB erhalten werden muss.">Antwort</span></li> <li>Was ist ein superskalarer Prozessor? &rarr; <span class="hint" title="Ein Prozessor, der pro Takt mehrere allgemeine Register schreiben und lesen kann.">Antwort</span></li> <li>Was ist ein little Endian und was ist big Endian? &rarr; <span class="hint" title="Das MSB bei little Endian ist ganz links, bei big Endian ganz rechts.">Antwort</span></li> <li>Was versteht man unter dem Nulladressformat? &rarr; <span class="hint" title="Die Befehlss&auml;tze, die nur aus dem Opcode bestehen. Das Einadressformat hat z.B. zus&auml;tzlich noch die Src.">Antwort</span></li> <li>Was ist eine &bdquo;effektive Adresse&ldquo;? &rarr; <span class="hint" title="Die Effektive Adresse ist die durch die Addressierungsart spezifizierte Adresse im Hauptspeicher. Sie entsteht im Prozessor nach Ausf&uuml;hrung der Adressierung.">Antwort</span></li> <li>Was bedeutet <span class="hint" title="Zero flag; Wichtig f&uuml;r Schleifen">ZF</span>, <span class="hint" title="Carry flag; set if an arithmetic operation generats a carry or a borrow out of the MSB of the result">CF</span>, <span class="hint" title="Sign flag; set equal to the MSB">SF</span>, <span class="hint" title="Overflow flag; set if the integer result is too large a positive number or too small a negative number to fit in the destination operand">OF</span> und wozu sind sie jeweils gut?</li> <li>Was ist eine Load/Store-Architektur? &rarr; <abbr title="Eine Load/Store Architektur ist eine Computerarchitektur, deren Befehlssatz Daten-Speicherzugriffe ausschlie&szlig;lich mit speziellen Lade- und Speicher-Befehlen erlaubt.">Antwort</abbr></li> <li>Was sind die f&uuml;nf Schritte in der DLX-Pipeline-Verarbeitung? &rarr; <abbr title="IF: Instruction fetch; ID/RF: Instruction decode/Register fetch; EX: Execute / address calculation; MEM: Memory access; WB: Write Back">Antwort</abbr></li> <li>In welcher Pipeline-Phase werden die Operanden aus dem memory geholt? &rarr; <abbr title="Tja, das war fies. Es ist nicht die MEM-Phase. In der MEM-Phase wird der Speicherzugriff von Lade- und Speicherbefehlen durchgef&uuml;hrt. Richtig ist: Die zweite Takth&auml;lfte der ID-Phase.">Antwort</abbr></li> <li>Durch welche Abh&auml;ngigkeiten entstehen Verz&ouml;gerungen in der DLX-Pipeline und wann treten diese auf? &rarr; <abbr title="Daten-, Struktur- und Steuerflussabh&auml;ngigkeiten. Datenabh&auml;ngigkeiten treten auf, wenn ein Operand noch nicht verf&uuml;gbar ist. Strukturkonflikte treten auf, wenn zwei Pipeline-Stufen dieselbe Ressource ben&ouml;tigen, auf diese aber nur einmal zugegriffen werden kann. Steuerflusskonflikte treten bei Programmsteuerbefehlen auf. Dies kann z.B. der Fall sein wenn in der Holphase die Zieladresse des als n&auml;chstes auszuf&uuml;hrenden Befehls noch nicht berechnet ist oder wenn bei einem bedingtem Sprung noch nicht klar ist, ob dieser &uuml;berhaupt umgesetzt werden wird.">Antwort</abbr></li> <li>Was ist eine echte Datenabh&auml;ngigkeit, was eine Gegenabh&auml;ngigkeit und was eine Ausgabeabh&auml;ngigkeit? &rarr; <abbr title="Echte Datenabh&auml;ngigkeit: a = b + c; d = a + e. Gegenabh&auml;ngigkeit: b = a + c; a = d + e. Ausgabeabh&auml;ngigkeit: a = b + c; a = d + e">Antwort</abbr></li> <li>Was ist eine falsche Abh&auml;ngigkeit? &rarr; <abbr title="Eine Gegen- oder Ausgabeabh&auml;ngigkeit.">Antwort</abbr></li> <li>Treten bei echten Abh&auml;ngigkeiten immer Konflikte auf? &rarr; <abbr title="Nein. Es k&ouml;nnen z.B. gen&uuml;gend Befehle zwischen den beiden Abh&auml;ngigen sein.">Antwort</abbr></li> <li>Welche Konflikte gibt es und wann k&ouml;nnen sie auftreten? &rarr; <abbr title="Read-after-Write: Echte Abh&auml;ngigkeit; Write-after-Read: Gegenabh&auml;ngigkeit; Write-after-Write: Ausgabeabh&auml;ngigkeit">Antwort</abbr></li> <li>Welche Abh&auml;ngigkeiten k&ouml;nnen bei der DLX-Pipeline zu Konflikten f&uuml;hren? &rarr; <abbr title="Nur echte Abh&auml;ngigkeiten k&ouml;nnen in der DLX-Pipeline zu Konflikten f&uuml;hren.">Antwort</abbr></li> <li>Wie kann man Datenkonflikte durch Software l&ouml;sen? &rarr; <abbr title="Entweder durch einf&uuml;gen von nops (Leeroperationen) oder durch Umordnung der Befehle (Optimierung)">Antwort</abbr></li> <li>Wie kann man Datenkonflikte durch Hardware l&ouml;sen? &rarr; <abbr title="Interlocking oder stalling (Pipeline-Sperrung oder Pipeline-Leerlauf); Forwarding, ben&ouml;tigt aber noch interlocking">Antwort</abbr></li> <li>Nennen Sie ein Beispiel f&uuml;r einen Konflikt, der nicht durch Forwarding l&ouml;stbar ist? &rarr; <abbr title="load r2, B; add r2, r1, r2">Antwort</abbr></li> <li>Wie kann man Ressourcenkonflikte l&ouml;sen? &rarr; <abbr title="Arbitrierung mit Interlocking; &Uuml;bertaktung; Ressourcenreplizierung">Antwort</abbr></li> <li>Was bedeutet <span class="hint" title="Minimale Zeitdauer, die zwischen der fallenden Flanke von RAS bis zur Ausgabe der gew&uuml;nschten Daten vergeht">t<sub>RAC</sub></span>, <span class="hint" title="Minimale Zeitdauer von Beginn eines Zeilenzugriffs bis zum n&auml;chsten Zeilenzugriff (Zykluszeit)">t<sub>RC</sub></span>, <span class="hint" title="Minimale Zeitdauer, die zwischen der fallenden Flanke von CAS bis zur Ausgabe der gew&uuml;nschten Daten vergeht">t<sub>CAC</sub></span> und <span class="hint" title="Minimale Zeitdauer vom Beginn eines Spaltenzugriffs bis zum n&auml;chsten Spaltenzugriff (page mode cycle).">t<sub>PC</sub></span>?</li> <li>Wie versteht man unter Bus-Schn&uuml;ffeln? &rarr; <abbr title="Jeder Prozessor kontrolliert st&auml;ndig alle Adressen auf dem Bus um Speicherinkonsistenzen zu vermeiden. Siehe Bus snooping.">Antwort</abbr></li> </ul> <h3>MIPS</h3> <h4>Befehlsformate</h4> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/mips-befehlsformate-300x136.png"><img src="../images/2013/01/mips-befehlsformate-300x136.png" alt="MIPS Befehlsformate" width="" height="" class="size-medium wp-image-62151" /></a><p class="wp-caption-text">MIPS Befehlsformate<br />Quelle: <a href="http://ti.ira.uka.de/TI-2/Vorlesung/Vorlesung.php">Folien von Prof. Dr. Asfour</a></p></div> <p>Typ-R Befehle sind arithmetisch-logische Befehle wie add, sub, and, or sowie Vergleichsbefehle wie <abbr title="set on less than">slt</abbr>.</p> <p>Typ-I Befehle sind Lade- und Speicherbefehle sowie Verzweigungsbefehle: <code>lw $`rt, imm(`$rs)</code> <code>sw $`rt, imm(`$rs)</code> <code>beq $`rs, `$rt, immediate</code>: Hier wird immediate als 16-Bit vorzeichenbehaftete Zahl interpretiert und als Offset benutzt. Die Basisadresse ist dabei im PC. Also lautet die Zieladresse: (PC zum Zeitpunkt des Befehls + 4) + immediate</p> <h4>Grundlegende Befehle</h4> <table> <thead> <tr> <th>Syntax</th> <th>Erkl&auml;rung</th> </tr> </thead> <tbody> <tr> <td>li $`t0, 9</td> <td>load immediate: L&auml;dt eine Konstante in ein Register</td> </tr> <tr> <td>sll `$rd, $`rd, shamt</td> <td>shift left logical: `$rd = $`rs &lt;&lt; shamt</td> </tr> <tr> <td>ble Rsrc1, Src2, label</td> <td>Branch on Less Than Equal: Rsrc1 &le; Src2</td> </tr> <tr> <td>bne `$rs, $`rt, imm</td> <td>Branch on not equal: if(`$rs!=$`rt) PC = PC + imm (imm could also be a label)</td> </tr> <tr> <td>slti `$rt, $`rs, imm</td> <td>Store less than immediate: if(`$rs &lt; imm) {$`rt = 1;} else {$rt = 0}</td> </tr> <tr> <td>la Rdest, address</td> <td>Load computed address, not the contents of the location, into register Rdest</td> </tr> </tbody> </table> <h3>MiMa</h3> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/mima-microbefehlsformat-300x35.png"><img src="../images/2013/01/mima-microbefehlsformat-300x35.png" alt="Mikrobefehlsformat der MiMa" width="" height="" class="size-medium wp-image-62571" /></a><p class="wp-caption-text">Mikrobefehlsformat der MiMa<br />Quelle: <a href="http://ti.ira.uka.de/TI-2/Vorlesung/RO-U01.pdf#page=15">Folien von Prof. Dr. Asfour</a></p></div> <h4>Fetch-Phase</h4> <p>In der Fetch-Phase muss das die neue Instruktion ins <abbr title="Instruktionsregister">IR</abbr> geladen werden und der <abbr title="Program counter">PC</abbr> um eins erhöht werden:</p> <ol> <li>Takt: IAR &rarr; SAR; IAR &rarr; X; R = 1</li> <li>Takt: Eins &rarr; Y; ALU auf addieren; R = 1</li> <li>Takt: ALU auf addieren; R = 1</li> <li>Takt: Z &rarr; IAR</li> <li>Takt: SDR &rarr; IR</li> </ol> <p>Das zugehörige Mikroprogramm ist:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">0010 0001 0000 1000 1000 0000 0001 0001 0100 0000 0000 1000 0000 0010 0000 0000 0000 0001 1000 0000 0011 0000 1010 0000 0000 0000 0000 0100 0000 0000 1001 0000 0000 0000 0101</code></pre></div> <h2>Fragen</h2> <div class="question"> <span class="question">Zeichnen Sie ein Y-Diagramm.</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/y-diagramm-300x206.png"><img src="../images/2013/01/y-diagramm-300x206.png" alt="Y-Diagramm" width="" height="" class="size-medium wp-image-61531" /></a><p class="wp-caption-text">Y-Diagramm<br />Quelle: <a href="http://ti.ira.uka.de/TI-2/Vorlesung/Vorlesung.php">Folien von Prof. Dr. Asfour</a></p></div> </div> </div> <div class="question"> <span class="question">Wie ist ein Von-Neumann-Rechner aufgebaut?</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/von-neumann-architektur-300x228.png"><img src="../images/2013/01/von-neumann-architektur-300x228.png" alt="Von-Neumann-Architektur" width="" height="" class="size-medium wp-image-61711" /></a><p class="wp-caption-text">Von-Neumann-Architektur</p></div> Das Steuerwerk wird auch &bdquo;Leitwerk&ldquo; genannt, das Rechenwerk auch &bdquo;<strong>A</strong>rithmetic <strong>L</strong>ogic <strong>U</strong>nit&ldquo;. Der BUS beinhaltet Adress-, Daten- und Steuerleitungen. Im Gegensatz zur Harvard-Architektur wird beim Speicher in der Von-Neumann-Architektur nicht zwischen Daten und Programmen unterschieden. </div> </div> <div class="question"> <span class="question">Wie ist ein Mikroprozessor aufgebaut?</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/aufbau-mikroprozessor-300x212.png"><img src="../images/2013/01/aufbau-mikroprozessor-300x212.png" alt="Aufbau eines Mikroprozessors" width="" height="" class="size-medium wp-image-61841" /></a><p class="wp-caption-text">Aufbau eines Mikroprozessors<br />Quelle: <a href="http://ti.ira.uka.de/TI-2/Vorlesung/RO-VL06.pdf#page=10">Folien von Prof. Dr. Asfour</a></p></div> </div> </div> <div class="question"> <span class="question">Aus welchen Phasen besteht die Befehlsausf&uuml;hrung?</span> <div class="answer"> <ul> <li>Holphase</li> <li>Dekodierphase</li> <li>Ausf&uuml;hrungsphase</li> </ul> </div> </div> <div class="question"> <span class="question">Warum gibt es mehr als ein Befehlsregister?</span> <div class="answer"> <ul> <li>Die Befehlsformate sind unterschiedlich lang</li> <li>Opcode-Prefetching</li> </ul> </div> </div> <div class="question"> <span class="question">Was ist der Unterschied zwischen BCD in gepackter Darstellung und BCD in ungepackter Darstellung?</span> <div class="answer"> Bei BCD in gepackter Darstellung werden in einem Byte (8 Bit) zwei BCD-Zahlen dargestellt. In der ungepackten Darstellung wird in einem Byte nur eine BCD-Zahl dargestellt. </div> </div> <div class="question"> <span class="question">Pipeline-Konflikte: Welche Forwarding-Techniken gibt es und wie werden sie umgesetzt?</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/forwarding-techniken2-300x249.png"><img src="../images/2013/01/forwarding-techniken2-300x249.png" alt="Forwarding-Techniken" width="" height="" class="size-medium wp-image-62451" /></a><p class="wp-caption-text">Forwarding-Techniken<br />Quelle: Quelle: <a href="http://ti.ira.uka.de/TI-2/Vorlesung/RO-VL06.pdf#page=10">Folien von Prof. Dr. Asfour</a></p></div> </div> </div> <div class="question"> <span class="question">Welche Halbleiterspeichertypen gibt es?</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/halbleiterspeicher-klassifizierung-300x77.png"><img src="../images/2013/01/halbleiterspeicher-klassifizierung-300x77.png" alt="Klassifizierung von Halbleiterspeicher" width="" height="" class="size-medium wp-image-62511" /></a><p class="wp-caption-text">Klassifizierung von Halbleiterspeicher</p></div> </div> </div> <div class="question"> <span class="question">Skizzieren Sie eine SRAM-Zelle.</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/cmos-sram-cell-300x300.png"><img src="../images/2013/01/cmos-sram-cell-300x300.png" alt="CMOS SRAM Zelle" width="" height="" class="size-medium wp-image-62521" /></a><p class="wp-caption-text">CMOS SRAM Zelle</p></div> </div> </div> <div class="question"> <span class="question">Wie unterscheiden sich RISC- und CISC-Architekturen?</span> <div class="answer"> <table> <thead> <tr> <th>CISC</th> <th>RISC</th> </tr> </thead> <tbody> <tr> <td>Komplexe Befehle, die in mehreren Taktzyklen ausgef&uuml;hrt werden</td> <td>Einfache Befehle, die in einem Taktzyklus ausgef&uuml;hrt werden</td> </tr> <tr> <td>Jeder Befehl kann auf den Speicher zugreifen</td> <td>Nur Lade- und Speicherbefehle greifen auf den Speicher zu</td> </tr> <tr> <td>Wenig Pipelining</td> <td>Intensives Pipelining</td> </tr> <tr> <td>Befehle werden von einem Mikroprogramm interpretiert</td> <td>Befehle werden durch festverdrahtete Hardware ausgef&uuml;hrt</td> </tr> <tr> <td>Befehlsformat variabler L&auml;nge</td> <td>Befehlsformat fester L&auml;nge</td> </tr> <tr> <td>Die Komplexit&auml;t liegt im Mikroprogramm</td> <td>Die Komplexit&auml;t liegt im Compiler</td> </tr> <tr> <td>Einfacher Registersatz</td> <td>Mehrere Registers&auml;tze</td> </tr> </tbody> </table> </div> </div> <div class="question"> <span class="question">Wie sieht das Schaltsymbol eines Halbaddierers aus?</span> <div class="answer"> <div style="width: 298px" class="wp-caption aligncenter"><a href="../images/2013/01/addierer-schaltsymbol.png"><img src="../images/2013/01/addierer-schaltsymbol.png" alt="Schaltsymbol eines Halbaddierers" width="" height="" class="size-full wp-image-62671" /></a><p class="wp-caption-text">Schaltsymbol eines Halbaddierers</p></div> </div> </div> <div class="question"> <span class="question">Wie kann man die Datenabh&auml;ngigkeiten einer Pipeline spezifizieren und erkennen?</span> <div class="answer"> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/ti-pipeline-datenabhaengigkeit-300x121.jpg"><img src="../images/2013/01/ti-pipeline-datenabhaengigkeit-300x121.jpg" alt="Datenabhaengigkeiten in einer Pipeline" width="" height="" class="size-medium wp-image-62791" /></a><p class="wp-caption-text">Datenabhaengigkeiten in einer Pipeline</p></div> Erkennen kann man sie sehr schnell, indem man eine Tabelle mit den Spalten Befehl, Ziel-Register und Operanden-Register macht. Dabei muss man insbesondere bei der Multiplikation, <code>sw</code> und <code>lw</code> aufpassen. Folgendes (sehr gekrizeltes) Beispiel f&uuml;r die <a href="http://ti.ira.uka.de/Klausur/AlteKlausuren/k_ss_12.pdf#page=11">Klausur vom 26. Juli 2012</a>: <div style="width: 522px" class="wp-caption alignnone"><a href="../images/2013/01/datenabhaengigkeiten-erkennen.jpg"><img src="../images/2013/01/datenabhaengigkeiten-erkennen.jpg" alt="Datenabh&auml;ngigkeiten schnell erkennen" width="" height="" class="size-full wp-image-63101" /></a><p class="wp-caption-text">Datenabh&auml;ngigkeiten schnell erkennen</p></div> </div> </div> <h2>Material</h2> <ul> <li><a href="http://ti.ira.uka.de/">TI-Website</a> <ul> <li><a href="http://ti.ira.uka.de/Klausur/AlteKlausuren/AlteKlausuren.php">alte Klausuren</a></li> <li><a href="http://ti.ira.uka.de/Adressierungsarten/">Flash-Animation zur Adressierung</a></li> </ul> </li> <li><a href="https://ankiweb.net/shared/info/144985236">Meine Karteikarten</a> (Siehe Anki auf <a href="http://de.wikipedia.org/wiki/Anki">Wikipedia</a> und <a href="http://wiki.ubuntuusers.de/Anki">UbuntuUsers</a> f&uuml;r mehr Informationen)</li> <li><a href="http://www.titut.de/">titut.de</a>, <a href="http://tutorium.chrismandery.de/">tutorium.chrismandery.de</a></li> </ul> <p>StackOverflow:</p> <ul> <li><a href="http://stackoverflow.com/q/4115847/562769">Strange jump in MIPS assembly</a></li> </ul> <h2>Aufbau der Klausur</h2> <p>Die Klausuren sind alle sehr ähnlich aufgebaut. Eine typische Klausur hat 10 Aufgaben zu diesen Themen:</p> <ol> <li><strong>Schaltfunktionen</strong></li> <li><strong>Spezielle Bausteine</strong></li> <li><strong>Laufzeiteffekte</strong></li> <li><strong>Schaltwerke</strong></li> <li><strong>Rechnerarithmetik und Codes</strong></li> <li><strong>Allgemeines</strong>: Ankreuzaufgaben</li> <li><strong>MIPS-Assembler</strong>: C-Code in MIPS umwandeln und umgekehrt</li> <li><strong>Pipelining</strong>: Datenkonflikte erkennen und mit NOPs beheben, eventuell gibts noch Forwarding</li> <li><strong>Cache-Speicher</strong></li> <li><strong>Speicher</strong></li> </ol> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Mittwoch, den 3. April 2013 von 14:00 bis 16:00 Uhr <strong>Ort</strong>: <a href="http://kit.carstengriesheimer.de/map/1458">Gaede</a> (bei mir; siehe <a href="http://ti.ira.uka.de/Klausur/Hoersaalverteilung.htm">Hörsaaleinteilung</a>, die seit dem 2. April 2013 draußen ist) <strong>Dauer</strong>: 1 h DT, 1 h RO <strong>Punkte</strong>: (vermutlich) 90 <strong>Bestehensgrenze</strong>: (vermutlich) 40 <strong>Übungsschein</strong>: Wird nicht ins Studienportal eingetragen <strong>Bonuspunkte</strong>:</p> <ul> <li>&Uuml;bungsschein RO: 1 Bonuspunkt</li> <li>&Uuml;bungsschein DT: 1 Bonuspunkt</li> <li>F&uuml;r die Probeklausuren jeweils: <ul> <li>Note &bdquo;Sehr gut&ldquo;: 2 Bonuspunkte</li> <li>Note &bdquo;Gut&ldquo;: 1,5 Bonuspunkte</li> <li>Note &bdquo;Befriedigend&ldquo;: 1 Bonuspunkt</li> <li>Note &bdquo;Ausreichend&ldquo;: 0,5 Bonuspunkte</li> </ul> </li> </ul> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Ergebnisse</h2> <p>Die Klausureinsicht ist am Montag, den 29. April 2013. Für die Einsicht muss man sich <a href="http://ti.ira.uka.de/Klausur/Einsicht/">hier</a> anmelden.</p> Software Licenses //martin-thoma.com/software-licenses/ Sat, 26 Jan 2013 09:59:46 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/software-licenses <p>Do you know the difference between MIT-license and BSD license? I don’t. And I don’t want to read the <a href="http://en.wikipedia.org/wiki/MIT_License">MIT license</a>, although it is very short. And I definitely don’t want to read the <a href="http://directory.fsf.org/wiki/License:Apache2.0">Apache 2.0 license</a>.</p> <p>Instead of reading all licenses, you could first read <a href="http://www.smashingmagazine.com/2010/03/24/a-short-guide-to-open-source-and-similar-licenses/">A Short Guide To Open-Source And Similar Licenses</a>.</p> <p>Even shorter: <a href="http://www.tldrlegal.com/">TL;DR - Open Source Licenses Explained in Plain English</a>.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/TLDRLegal-300x158.png"><img src="../images/2013/01/TLDRLegal-300x158.png" alt="TL;DR Legal" width="" height="" class="size-medium wp-image-55141" /></a><p class="wp-caption-text">TL;DR Legal</p></div> <p>Licenses are important for OpenSource, because if you don’t provide a license, nobody may use your source (<a href="http://stackoverflow.com/a/13669816/562769">source</a>). So even if everybody can see your code, it is not OpenSource if you don’t choose an OpenSource license.</p> <p>I think Jeff Atwood has written an article about the fact, that many GitHub projects are not OpenSource due to a missing license. Sadly, I don’t find the article. But here is another one by him: <a href="http://www.codinghorror.com/blog/2007/04/pick-a-license-any-license.html">Pick a License, Any License</a></p> Part II: The Strassen algorithm in Python, Java and C++ //martin-thoma.com/strassen-algorithm-in-python-java-cpp/ Wed, 23 Jan 2013 10:35:55 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/strassen-algorithm-in-python-java-cpp <div class="info">This is Part II of my matrix multiplication series. <a href="../matrix-multiplication-python-java-cpp/">Part I</a> was about simple matrix multiplication algorithms and <a href="../strassen-algorithm-in-python-java-cpp/">Part II</a> was about the Strassen algorithm. <a href="../part-iii-matrix-multiplication-on-multiple-cores-in-python-java-and-c/">Part III</a> is about parallel matrix multiplication.</div> <p>The usual matrix multiplication of two <code>$n \times n$</code> matrices has a time-complexity of <code>$\mathcal{O}(n^3)$</code>. This means, if <code>$n$</code> doubles, the time for the computation increases by a factor of 8. But you don’t have to use that much resources. The <a href="http://en.wikipedia.org/wiki/Strassen_algorithm">Strassen algorithm</a> has a time complexity of <code>$\mathcal O(n^{log_2(7)+o(1)}) \approx \cal O(n^{2.807})$</code>. The idea is similar to the <a href="http://en.wikipedia.org/wiki/Karatsuba_algorithm">Karatsuba algorithm</a> for simple multiplication. Basically, you make a tradeof: Instead of one multiplication, you use many additions. As additions are - at least for humans - easier, you might rather like to use many additions. Lets see how the Strassen algortihms execution time compares to the other execution times in Part I. As last time, I’ll multiply two <code>$2000 \times 2000$</code> matrices that have to be read from a file. Everything - reading, calculation and writing the result - counts to the execution time.</p> <h2>The implementations</h2> <p>As last time, I’ve added the scripts to a <a href="https://github.com/MartinThoma/matrix-multiplication">GIT repository</a>, so feel free to test it on your machine. I will use the I am also happy if you post some of your solutions with running times ☺ If you know other languages, you could create a script for these. I focus on Python, Java and C++.</p> <p>I have implemented only the Strassen algorithm for this post. Please take a look at Wikipedia for a detailed explanation how this algorithm works. The important idea of the algorithm is that you break both matrices into four <code>$\frac{n}{2} \times \frac{n}{2}$</code> matrices and multiply them in a clever way. Note that you can also use the Strassen algorithm recursively for those <code>$\frac{n}{2} \times \frac{n}{2}$</code> matrices. You can do this until you have <code>$1 \times 1$</code> matrices which are simple numbers. But it does make sense to stop this recursion and use the <a href="../matrix-multiplication-python-java-cpp/#ikj-algorithm">ikj-algorithm</a> as soon as the matrices are small enough. But what exactly is “small enough”? I’ll test that. The size when you use the ikj-algorithm is called <code>LEAF_SIZE</code> in my scripts. Note that only leaf sizes of multiples of two matter as the size of the (sub-)matrices that get passed to strassenR are multiples of two.</p> <p>If you post a solution, please consider these restrictions:</p> <ul> <li><strong>Input</strong>: <ul> <li>The input file should get passed with the parameter <code>-i</code>, e.g.: <code>python -i bigMatrix.in</code> or <code>java Shell -i bigMatrix.in</code></li> <li>The leaf-size should get passed with <code>-l</code>, e.g.: <code>python -i bigMatrix.in -l 32</code></li> </ul> </li> <li>The standard value for the command line parameter -i should be "bigMatrix.in"</li> <li>The user should <em>not</em> have to give the size of the matrix!</li> <li>The two square-matrices that should get multiplied are ... <ul> <li>... read from a text-file.</li> <li>... represented like this: <ul> <li>Every line of one matrix is one line in the text-file.</li> <li>Newlines are only "\n".</li> <li>Every number is separated by "\t".</li> <li>The both matrices are separated by one newline.</li> </ul> </li> </ul> </li> <li><strong>Output</strong>: The result has to get printed to standard output.</li> <li>The result has to be formatted like the input (tabs for separation of number, \n for marks a new line)</li> </ul> <h2>Tests and Setting</h2> <p><a href="../matrix-multiplication-python-java-cpp/#The_Tests">Tests and setting</a> are the same as in the first part.</p> <h2>Python</h2> <p>I’ve used Python 2.6.5.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">optparse</span> <span class="kn">import</span> <span class="n">OptionParser</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">ceil</span><span class="p">,</span> <span class="n">log</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">A</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="k">if</span> <span class="n">line</span> <span class="o">!=</span> <span class="s">&quot;&quot;</span><span class="p">:</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">else</span><span class="p">:</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">):</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="k">def</span> <span class="nf">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="k">def</span> <span class="nf">add</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="k">def</span> <span class="nf">subtract</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="k">def</span> <span class="nf">strassenR</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; </span> <span class="sd"> Implementation of the strassen algorithm.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&lt;=</span> <span class="n">LEAF_SIZE</span><span class="p">:</span> <span class="k">return</span> <span class="n">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="c"># initializing the new sub-matrices</span> <span class="n">newSize</span> <span class="o">=</span> <span class="n">n</span><span class="o">/</span><span class="mi">2</span> <span class="n">a11</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">a12</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">a21</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">a22</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">b11</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">b12</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">b21</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">b22</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">aResult</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="n">bResult</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">)]</span> <span class="c"># dividing the matrices in 4 sub-matrices:</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">):</span> <span class="n">a11</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="c"># top left</span> <span class="n">a12</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">]</span> <span class="c"># top right</span> <span class="n">a21</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="c"># bottom left</span> <span class="n">a22</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">]</span> <span class="c"># bottom right</span> <span class="n">b11</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="c"># top left</span> <span class="n">b12</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">]</span> <span class="c"># top right</span> <span class="n">b21</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="c"># bottom left</span> <span class="n">b22</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">]</span> <span class="c"># bottom right</span> <span class="c"># Calculating p1 to p7:</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">a11</span><span class="p">,</span> <span class="n">a22</span><span class="p">)</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">b11</span><span class="p">,</span> <span class="n">b22</span><span class="p">)</span> <span class="n">p1</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">bResult</span><span class="p">)</span> <span class="c"># p1 = (a11+a22) * (b11+b22)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">a21</span><span class="p">,</span> <span class="n">a22</span><span class="p">)</span> <span class="c"># a21 + a22</span> <span class="n">p2</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">b11</span><span class="p">)</span> <span class="c"># p2 = (a21+a22) * (b11)</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="p">(</span><span class="n">b12</span><span class="p">,</span> <span class="n">b22</span><span class="p">)</span> <span class="c"># b12 - b22</span> <span class="n">p3</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">a11</span><span class="p">,</span> <span class="n">bResult</span><span class="p">)</span> <span class="c"># p3 = (a11) * (b12 - b22)</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="p">(</span><span class="n">b21</span><span class="p">,</span> <span class="n">b11</span><span class="p">)</span> <span class="c"># b21 - b11</span> <span class="n">p4</span> <span class="o">=</span><span class="n">strassenR</span><span class="p">(</span><span class="n">a22</span><span class="p">,</span> <span class="n">bResult</span><span class="p">)</span> <span class="c"># p4 = (a22) * (b21 - b11)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">a11</span><span class="p">,</span> <span class="n">a12</span><span class="p">)</span> <span class="c"># a11 + a12</span> <span class="n">p5</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">b22</span><span class="p">)</span> <span class="c"># p5 = (a11+a12) * (b22) </span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="p">(</span><span class="n">a21</span><span class="p">,</span> <span class="n">a11</span><span class="p">)</span> <span class="c"># a21 - a11</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">b11</span><span class="p">,</span> <span class="n">b12</span><span class="p">)</span> <span class="c"># b11 + b12</span> <span class="n">p6</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">bResult</span><span class="p">)</span> <span class="c"># p6 = (a21-a11) * (b11+b12)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="p">(</span><span class="n">a12</span><span class="p">,</span> <span class="n">a22</span><span class="p">)</span> <span class="c"># a12 - a22</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">b21</span><span class="p">,</span> <span class="n">b22</span><span class="p">)</span> <span class="c"># b21 + b22</span> <span class="n">p7</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">bResult</span><span class="p">)</span> <span class="c"># p7 = (a12-a22) * (b21+b22)</span> <span class="c"># calculating c21, c21, c11 e c22:</span> <span class="n">c12</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">p3</span><span class="p">,</span> <span class="n">p5</span><span class="p">)</span> <span class="c"># c12 = p3 + p5</span> <span class="n">c21</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">p2</span><span class="p">,</span> <span class="n">p4</span><span class="p">)</span> <span class="c"># c21 = p2 + p4</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">p1</span><span class="p">,</span> <span class="n">p4</span><span class="p">)</span> <span class="c"># p1 + p4</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">p7</span><span class="p">)</span> <span class="c"># p1 + p4 + p7</span> <span class="n">c11</span> <span class="o">=</span> <span class="n">subtract</span><span class="p">(</span><span class="n">bResult</span><span class="p">,</span> <span class="n">p5</span><span class="p">)</span> <span class="c"># c11 = p1 + p4 - p5 + p7</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">p1</span><span class="p">,</span> <span class="n">p3</span><span class="p">)</span> <span class="c"># p1 + p3</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">p6</span><span class="p">)</span> <span class="c"># p1 + p3 + p6</span> <span class="n">c22</span> <span class="o">=</span> <span class="n">subtract</span><span class="p">(</span><span class="n">bResult</span><span class="p">,</span> <span class="n">p2</span><span class="p">)</span> <span class="c"># c22 = p1 + p3 - p2 + p6</span> <span class="c"># Grouping the results obtained in a single matrix:</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">newSize</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">c11</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">]</span> <span class="o">=</span> <span class="n">c12</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">c21</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="p">]</span> <span class="o">=</span> <span class="n">c22</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="k">def</span> <span class="nf">strassen</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="k">assert</span> <span class="nb">type</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="o">==</span> <span class="nb">list</span> <span class="ow">and</span> <span class="nb">type</span><span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="o">==</span> <span class="nb">list</span> <span class="k">assert</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="o">==</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="o">==</span> <span class="nb">len</span><span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="o">==</span> <span class="nb">len</span><span class="p">(</span><span class="n">B</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="c"># Make the matrices bigger so that you can apply the strassen</span> <span class="c"># algorithm recursively without having to deal with odd</span> <span class="c"># matrix sizes</span> <span class="n">nextPowerOfTwo</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">:</span> <span class="mi">2</span><span class="o">**</span><span class="nb">int</span><span class="p">(</span><span class="n">ceil</span><span class="p">(</span><span class="n">log</span><span class="p">(</span><span class="n">n</span><span class="p">,</span><span class="mi">2</span><span class="p">)))</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">m</span> <span class="o">=</span> <span class="n">nextPowerOfTwo</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="n">APrep</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">m</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">m</span><span class="p">)]</span> <span class="n">BPrep</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">m</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">m</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">APrep</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="n">BPrep</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="n">CPrep</span> <span class="o">=</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">APrep</span><span class="p">,</span> <span class="n">BPrep</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">CPrep</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">OptionParser</span><span class="p">()</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_option</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;2000.in&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_option</span><span class="p">(</span><span class="s">&quot;-l&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;LEAF_SIZE&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;8&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;when do you start using ikj&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;LEAF_SIZE&quot;</span><span class="p">)</span> <span class="p">(</span><span class="n">options</span><span class="p">,</span> <span class="n">args</span><span class="p">)</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="n">LEAF_SIZE</span> <span class="o">=</span> <span class="n">options</span><span class="o">.</span><span class="n">LEAF_SIZE</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">options</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">strassen</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">)</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">)</span></code></pre></div> <p>The execution-times were the same as with the ikj-algorithm, no matter what the leaf size was:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">ikj-algorithm 44m13.458s LEAF_SIZE Time 2 47m45.983s 8 47m41.311s 16 48m5.472s 32 48m5.624s 64 47m55.076s</code></pre></div> <h2>Java</h2> <p>The Java-code is a little bit long and has three classes. I’ll only past the important methods. If you’re interested in a full, working example, please look at <a href="https://github.com/MartinThoma/matrix-multiplication/tree/master/Java">GitHub</a>.</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">ikjAlgorithm</span><span class="o">(</span><span class="kt">int</span><span class="o">[][]</span> <span class="n">A</span><span class="o">,</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">length</span><span class="o">;</span> <span class="c1">// initialise C</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">k</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">+=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">k</span><span class="o">]</span> <span class="o">*</span> <span class="n">B</span><span class="o">[</span><span class="n">k</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">private</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">add</span><span class="o">(</span><span class="kt">int</span><span class="o">[][]</span> <span class="n">A</span><span class="o">,</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">length</span><span class="o">;</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">+</span> <span class="n">B</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">private</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">subtract</span><span class="o">(</span><span class="kt">int</span><span class="o">[][]</span> <span class="n">A</span><span class="o">,</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">length</span><span class="o">;</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">-</span> <span class="n">B</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">private</span> <span class="kd">static</span> <span class="kt">int</span> <span class="nf">nextPowerOfTwo</span><span class="o">(</span><span class="kt">int</span> <span class="n">n</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">log2</span> <span class="o">=</span> <span class="o">(</span><span class="kt">int</span><span class="o">)</span> <span class="n">Math</span><span class="o">.</span><span class="na">ceil</span><span class="o">(</span><span class="n">Math</span><span class="o">.</span><span class="na">log</span><span class="o">(</span><span class="n">n</span><span class="o">)</span> <span class="o">/</span> <span class="n">Math</span><span class="o">.</span><span class="na">log</span><span class="o">(</span><span class="mi">2</span><span class="o">));</span> <span class="k">return</span> <span class="o">(</span><span class="kt">int</span><span class="o">)</span> <span class="n">Math</span><span class="o">.</span><span class="na">pow</span><span class="o">(</span><span class="mi">2</span><span class="o">,</span> <span class="n">log2</span><span class="o">);</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">strassen</span><span class="o">(</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span><span class="o">,</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="c1">// Make the matrices bigger so that you can apply the strassen</span> <span class="c1">// algorithm recursively without having to deal with odd</span> <span class="c1">// matrix sizes</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">();</span> <span class="kt">int</span> <span class="n">m</span> <span class="o">=</span> <span class="n">nextPowerOfTwo</span><span class="o">(</span><span class="n">n</span><span class="o">);</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">APrep</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">m</span><span class="o">][</span><span class="n">m</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">BPrep</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">m</span><span class="o">][</span><span class="n">m</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">APrep</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="n">BPrep</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">CPrep</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">APrep</span><span class="o">,</span> <span class="n">BPrep</span><span class="o">);</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">CPrep</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">private</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">strassenR</span><span class="o">(</span><span class="kt">int</span><span class="o">[][]</span> <span class="n">A</span><span class="o">,</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">length</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">n</span> <span class="o">&lt;=</span> <span class="n">LEAF_SIZE</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="nf">ikjAlgorithm</span><span class="o">(</span><span class="n">A</span><span class="o">,</span> <span class="n">B</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="c1">// initializing the new sub-matrices</span> <span class="kt">int</span> <span class="n">newSize</span> <span class="o">=</span> <span class="n">n</span> <span class="o">/</span> <span class="mi">2</span><span class="o">;</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">a11</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">a12</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">a21</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">a22</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">b11</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">b12</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">b21</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">b22</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">aResult</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">bResult</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">newSize</span><span class="o">][</span><span class="n">newSize</span><span class="o">];</span> <span class="c1">// dividing the matrices in 4 sub-matrices:</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">newSize</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">newSize</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">a11</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="c1">// top left</span> <span class="n">a12</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">];</span> <span class="c1">// top right</span> <span class="n">a21</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="c1">// bottom left</span> <span class="n">a22</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">];</span> <span class="c1">// bottom right</span> <span class="n">b11</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">B</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="c1">// top left</span> <span class="n">b12</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">B</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">];</span> <span class="c1">// top right</span> <span class="n">b21</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">B</span><span class="o">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="c1">// bottom left</span> <span class="n">b22</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">B</span><span class="o">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">];</span> <span class="c1">// bottom right</span> <span class="o">}</span> <span class="o">}</span> <span class="c1">// Calculating p1 to p7:</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">a11</span><span class="o">,</span> <span class="n">a22</span><span class="o">);</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">b11</span><span class="o">,</span> <span class="n">b22</span><span class="o">);</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p1</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">bResult</span><span class="o">);</span> <span class="c1">// p1 = (a11+a22) * (b11+b22)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">a21</span><span class="o">,</span> <span class="n">a22</span><span class="o">);</span> <span class="c1">// a21 + a22</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p2</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">b11</span><span class="o">);</span> <span class="c1">// p2 = (a21+a22) * (b11)</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="o">(</span><span class="n">b12</span><span class="o">,</span> <span class="n">b22</span><span class="o">);</span> <span class="c1">// b12 - b22</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p3</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">a11</span><span class="o">,</span> <span class="n">bResult</span><span class="o">);</span> <span class="c1">// p3 = (a11) * (b12 - b22)</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="o">(</span><span class="n">b21</span><span class="o">,</span> <span class="n">b11</span><span class="o">);</span> <span class="c1">// b21 - b11</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p4</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">a22</span><span class="o">,</span> <span class="n">bResult</span><span class="o">);</span> <span class="c1">// p4 = (a22) * (b21 - b11)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">a11</span><span class="o">,</span> <span class="n">a12</span><span class="o">);</span> <span class="c1">// a11 + a12</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p5</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">b22</span><span class="o">);</span> <span class="c1">// p5 = (a11+a12) * (b22)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="o">(</span><span class="n">a21</span><span class="o">,</span> <span class="n">a11</span><span class="o">);</span> <span class="c1">// a21 - a11</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">b11</span><span class="o">,</span> <span class="n">b12</span><span class="o">);</span> <span class="c1">// b11 + b12</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p6</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">bResult</span><span class="o">);</span> <span class="c1">// p6 = (a21-a11) * (b11+b12)</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">subtract</span><span class="o">(</span><span class="n">a12</span><span class="o">,</span> <span class="n">a22</span><span class="o">);</span> <span class="c1">// a12 - a22</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">b21</span><span class="o">,</span> <span class="n">b22</span><span class="o">);</span> <span class="c1">// b21 + b22</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">p7</span> <span class="o">=</span> <span class="n">strassenR</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">bResult</span><span class="o">);</span> <span class="c1">// p7 = (a12-a22) * (b21+b22)</span> <span class="c1">// calculating c21, c21, c11 e c22:</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">c12</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">p3</span><span class="o">,</span> <span class="n">p5</span><span class="o">);</span> <span class="c1">// c12 = p3 + p5</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">c21</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">p2</span><span class="o">,</span> <span class="n">p4</span><span class="o">);</span> <span class="c1">// c21 = p2 + p4</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">p1</span><span class="o">,</span> <span class="n">p4</span><span class="o">);</span> <span class="c1">// p1 + p4</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">p7</span><span class="o">);</span> <span class="c1">// p1 + p4 + p7</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">c11</span> <span class="o">=</span> <span class="n">subtract</span><span class="o">(</span><span class="n">bResult</span><span class="o">,</span> <span class="n">p5</span><span class="o">);</span> <span class="c1">// c11 = p1 + p4 - p5 + p7</span> <span class="n">aResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">p1</span><span class="o">,</span> <span class="n">p3</span><span class="o">);</span> <span class="c1">// p1 + p3</span> <span class="n">bResult</span> <span class="o">=</span> <span class="n">add</span><span class="o">(</span><span class="n">aResult</span><span class="o">,</span> <span class="n">p6</span><span class="o">);</span> <span class="c1">// p1 + p3 + p6</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">c22</span> <span class="o">=</span> <span class="n">subtract</span><span class="o">(</span><span class="n">bResult</span><span class="o">,</span> <span class="n">p2</span><span class="o">);</span> <span class="c1">// c22 = p1 + p3 - p2 + p6</span> <span class="c1">// Grouping the results obtained in a single matrix:</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">newSize</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">newSize</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">c11</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">]</span> <span class="o">=</span> <span class="n">c12</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">c21</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newSize</span><span class="o">]</span> <span class="o">=</span> <span class="n">c22</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">];</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Here are the results for different leaf-sizes:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/01/bchart-simple.png"><img src="../images/2013/01/bchart-simple.png" alt="Matrix multiplication with Java: Execution time in seconds for different leafsizes" width="" height="" class="size-full wp-image-54901" /></a><p class="wp-caption-text">Matrix multiplication with Java: Execution time in seconds for different leafsizes</p></div> <h2>C++</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;sstream&gt;</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;fstream&gt;</span> <span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="cp">#include &lt;algorithm&gt;</span> <span class="cp">#include &lt;cmath&gt;</span> <span class="c1">// Set LEAF_SIZE to 1 if you want to the pure strassen algorithm</span> <span class="c1">// otherwise, the ikj-algorithm will be applied when the split</span> <span class="c1">// matrices are as small as LEAF_SIZE x LEAF_SIZE</span> <span class="kt">int</span> <span class="n">leafsize</span><span class="p">;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="cm">/*</span> <span class="cm"> * Implementation of the strassen algorithm, similar to </span> <span class="cm"> * http://en.wikipedia.org/w/index.php?title=Strassen_algorithm&amp;oldid=498910018#Source_code_of_the_Strassen_algorithm_in_C_language</span> <span class="cm"> */</span> <span class="kt">void</span> <span class="nf">strassen</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">);</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="nf">nextPowerOfTwo</span><span class="p">(</span><span class="kt">int</span> <span class="n">n</span><span class="p">);</span> <span class="kt">void</span> <span class="nf">strassenR</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">);</span> <span class="kt">void</span> <span class="nf">sum</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">);</span> <span class="kt">void</span> <span class="nf">subtract</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">);</span> <span class="kt">void</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">matrix</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">);</span> <span class="kt">void</span> <span class="nf">read</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">);</span> <span class="kt">void</span> <span class="nf">ikjalgorithm</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">strassenR</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">tam</span> <span class="o">&lt;=</span> <span class="n">leafsize</span><span class="p">)</span> <span class="p">{</span> <span class="n">ikjalgorithm</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">C</span><span class="p">,</span> <span class="n">tam</span><span class="p">);</span> <span class="k">return</span><span class="p">;</span> <span class="p">}</span> <span class="c1">// other cases are treated here:</span> <span class="k">else</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">newTam</span> <span class="o">=</span> <span class="n">tam</span><span class="o">/</span><span class="mi">2</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">inner</span> <span class="p">(</span><span class="n">newTam</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">a11</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">a12</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">a21</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">a22</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">b11</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">b12</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">b21</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">b22</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">c11</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">c12</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">c21</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">c22</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p1</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p2</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p3</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p4</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p5</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p6</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">p7</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">aResult</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">),</span> <span class="n">bResult</span><span class="p">(</span><span class="n">newTam</span><span class="p">,</span><span class="n">inner</span><span class="p">);</span> <span class="kt">int</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">;</span> <span class="c1">//dividing the matrices in 4 sub-matrices:</span> <span class="k">for</span> <span class="p">(</span><span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">newTam</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">newTam</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">a11</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">a12</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">];</span> <span class="n">a21</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">a22</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">];</span> <span class="n">b11</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">b12</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">];</span> <span class="n">b21</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">b22</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="c1">// Calculating p1 to p7:</span> <span class="n">sum</span><span class="p">(</span><span class="n">a11</span><span class="p">,</span> <span class="n">a22</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// a11 + a22</span> <span class="n">sum</span><span class="p">(</span><span class="n">b11</span><span class="p">,</span> <span class="n">b22</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// b11 + b22</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">p1</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p1 = (a11+a22) * (b11+b22)</span> <span class="n">sum</span><span class="p">(</span><span class="n">a21</span><span class="p">,</span> <span class="n">a22</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// a21 + a22</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">b11</span><span class="p">,</span> <span class="n">p2</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p2 = (a21+a22) * (b11)</span> <span class="n">subtract</span><span class="p">(</span><span class="n">b12</span><span class="p">,</span> <span class="n">b22</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// b12 - b22</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">a11</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">p3</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p3 = (a11) * (b12 - b22)</span> <span class="n">subtract</span><span class="p">(</span><span class="n">b21</span><span class="p">,</span> <span class="n">b11</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// b21 - b11</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">a22</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">p4</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p4 = (a22) * (b21 - b11)</span> <span class="n">sum</span><span class="p">(</span><span class="n">a11</span><span class="p">,</span> <span class="n">a12</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// a11 + a12</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">b22</span><span class="p">,</span> <span class="n">p5</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p5 = (a11+a12) * (b22) </span> <span class="n">subtract</span><span class="p">(</span><span class="n">a21</span><span class="p">,</span> <span class="n">a11</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// a21 - a11</span> <span class="n">sum</span><span class="p">(</span><span class="n">b11</span><span class="p">,</span> <span class="n">b12</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// b11 + b12</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">p6</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p6 = (a21-a11) * (b11+b12)</span> <span class="n">subtract</span><span class="p">(</span><span class="n">a12</span><span class="p">,</span> <span class="n">a22</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// a12 - a22</span> <span class="n">sum</span><span class="p">(</span><span class="n">b21</span><span class="p">,</span> <span class="n">b22</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// b21 + b22</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">p7</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p7 = (a12-a22) * (b21+b22)</span> <span class="c1">// calculating c21, c21, c11 e c22:</span> <span class="n">sum</span><span class="p">(</span><span class="n">p3</span><span class="p">,</span> <span class="n">p5</span><span class="p">,</span> <span class="n">c12</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// c12 = p3 + p5</span> <span class="n">sum</span><span class="p">(</span><span class="n">p2</span><span class="p">,</span> <span class="n">p4</span><span class="p">,</span> <span class="n">c21</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// c21 = p2 + p4</span> <span class="n">sum</span><span class="p">(</span><span class="n">p1</span><span class="p">,</span> <span class="n">p4</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p1 + p4</span> <span class="n">sum</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">p7</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p1 + p4 + p7</span> <span class="n">subtract</span><span class="p">(</span><span class="n">bResult</span><span class="p">,</span> <span class="n">p5</span><span class="p">,</span> <span class="n">c11</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// c11 = p1 + p4 - p5 + p7</span> <span class="n">sum</span><span class="p">(</span><span class="n">p1</span><span class="p">,</span> <span class="n">p3</span><span class="p">,</span> <span class="n">aResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p1 + p3</span> <span class="n">sum</span><span class="p">(</span><span class="n">aResult</span><span class="p">,</span> <span class="n">p6</span><span class="p">,</span> <span class="n">bResult</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// p1 + p3 + p6</span> <span class="n">subtract</span><span class="p">(</span><span class="n">bResult</span><span class="p">,</span> <span class="n">p2</span><span class="p">,</span> <span class="n">c22</span><span class="p">,</span> <span class="n">newTam</span><span class="p">);</span> <span class="c1">// c22 = p1 + p3 - p2 + p6</span> <span class="c1">// Grouping the results obtained in a single matrix:</span> <span class="k">for</span> <span class="p">(</span><span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">newTam</span> <span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="n">j</span> <span class="o">=</span> <span class="mi">0</span> <span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">newTam</span> <span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">c11</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">]</span> <span class="o">=</span> <span class="n">c12</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">c21</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">][</span><span class="n">j</span> <span class="o">+</span> <span class="n">newTam</span><span class="p">]</span> <span class="o">=</span> <span class="n">c22</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="nf">nextPowerOfTwo</span><span class="p">(</span><span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">pow</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="kt">int</span><span class="p">(</span><span class="n">ceil</span><span class="p">(</span><span class="n">log2</span><span class="p">(</span><span class="n">n</span><span class="p">))));</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">strassen</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="c1">//unsigned int n = tam;</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">m</span> <span class="o">=</span> <span class="n">nextPowerOfTwo</span><span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">inner</span><span class="p">(</span><span class="n">m</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">APrep</span><span class="p">(</span><span class="n">m</span><span class="p">,</span> <span class="n">inner</span><span class="p">),</span> <span class="n">BPrep</span><span class="p">(</span><span class="n">m</span><span class="p">,</span> <span class="n">inner</span><span class="p">),</span> <span class="n">CPrep</span><span class="p">(</span><span class="n">m</span><span class="p">,</span> <span class="n">inner</span><span class="p">);</span> <span class="k">for</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">APrep</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="n">BPrep</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="n">strassenR</span><span class="p">(</span><span class="n">APrep</span><span class="p">,</span> <span class="n">BPrep</span><span class="p">,</span> <span class="n">CPrep</span><span class="p">,</span> <span class="n">m</span><span class="p">);</span> <span class="k">for</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span><span class="o">&lt;</span><span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">CPrep</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">sum</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">tam</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">tam</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">subtract</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">C</span><span class="p">,</span> <span class="kt">int</span> <span class="n">tam</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">tam</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">tam</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">getMatrixSize</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">)</span> <span class="p">{</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="n">ifstream</span> <span class="n">infile</span><span class="p">;</span> <span class="n">infile</span><span class="p">.</span><span class="n">open</span> <span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">());</span> <span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">);</span> <span class="k">return</span> <span class="n">count</span><span class="p">(</span><span class="n">line</span><span class="p">.</span><span class="n">begin</span><span class="p">(),</span> <span class="n">line</span><span class="p">.</span><span class="n">end</span><span class="p">(),</span> <span class="sc">&#39;\t&#39;</span><span class="p">)</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">read</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="o">&amp;</span><span class="n">B</span><span class="p">)</span> <span class="p">{</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="kt">FILE</span><span class="o">*</span> <span class="n">matrixfile</span> <span class="o">=</span> <span class="n">freopen</span><span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">(),</span> <span class="s">&quot;r&quot;</span><span class="p">,</span> <span class="n">stdin</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">matrixfile</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">cerr</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Could not read file &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">filename</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">j</span><span class="p">,</span> <span class="n">a</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">cin</span><span class="p">,</span> <span class="n">line</span><span class="p">)</span> <span class="o">&amp;&amp;</span> <span class="o">!</span><span class="n">line</span><span class="p">.</span><span class="n">empty</span><span class="p">())</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">a</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">cin</span><span class="p">,</span> <span class="n">line</span><span class="p">))</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">a</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">fclose</span> <span class="p">(</span><span class="n">matrixfile</span><span class="p">);</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">matrix</span><span class="p">,</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">j</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">matrix</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span> <span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="n">string</span> <span class="n">filename</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">&lt;</span> <span class="mi">3</span><span class="p">)</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;2000.in&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">argv</span><span class="p">[</span><span class="mi">2</span><span class="p">];</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">&lt;</span> <span class="mi">5</span><span class="p">)</span> <span class="p">{</span> <span class="n">leafsize</span> <span class="o">=</span> <span class="mi">16</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">leafsize</span> <span class="o">=</span> <span class="n">atoi</span><span class="p">(</span><span class="n">argv</span><span class="p">[</span><span class="mi">4</span><span class="p">]);</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">getMatrixSize</span><span class="p">(</span><span class="n">filename</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">inner</span> <span class="p">(</span><span class="n">n</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">inner</span><span class="p">),</span> <span class="n">B</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">inner</span><span class="p">),</span> <span class="n">C</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">inner</span><span class="p">);</span> <span class="n">read</span> <span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">);</span> <span class="n">strassen</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">C</span><span class="p">,</span> <span class="n">n</span><span class="p">);</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">,</span> <span class="n">n</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>For C++, you get those user-times for the different leaf-sizes:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2013/01/cpp-leaf-size-times.png"><img src="../images/2013/01/cpp-leaf-size-times.png" alt="Execution times in seconds with differen leafsizes with C++" width="" height="" class="size-full wp-image-54921" /></a><p class="wp-caption-text">Execution times in seconds with differen leafsizes with C++</p></div> <h2>Conclusion</h2> <p>As always, C++ is the fastest solution.</p> <p>I am a little bit surprised, that the LEAF_SIZE doesn’t matter for Python. I think I have used some very slow operations that are much more important than any speed gains or losses due to LEAF_SIZE. I guess the list creation might be slow. Does anybody know a tool for performance analysis of Python programs? This tool should be able to track which pieces of code got executed most often any preferably visualize it.</p> <p>For Java and C++, the Strassen algorithm had better execution times than the ikj-algorithm and it was also better than any library that I could find. The reasons why librarys perform worse than my implementation might be that pure integer matrices are rather rare. Usually you have double-matrices. Maybe you use different algorithms to keep rounding errors as small as possible (Can anybody provide more information to my speculations?)</p> <p>Leafsizes from 64 to 256 seem to be the best solution.</p> Check x-in-a-row for board games //martin-thoma.com/check-x-in-a-row-for-board-games/ Mon, 21 Jan 2013 21:59:28 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/check-x-in-a-row-for-board-games <p>In board games, you have quite often the situation that you want to check something in different directions. Most of the time, the implementation I see for situations like this is very redundant and prone to off-by-one errors. Some simple ideas can improve the quality of codes (code that is easier to understand and less <abbr title="lines of code">loc</abbr>) and reduce the probability of tiny mistakes.</p> <ul class="gallery mw-gallery-traditional"><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/01/tic-tac-toe.png" class="image"><img src="//martin-thoma.com/captions/tic-tac-toe.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Tic Tac Toe</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/01/battleships.png" class="image"><img src="//martin-thoma.com/captions/battleships.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Battleships</div></div></li><li class="gallerybox" style="width: 155px"><div style="width: 155px"><div class="thumb" style="width: 150px;"><div style="margin:21px auto;height: 113px;line-height: 150px;"><a href="../images/2013/01/queens-moves.png" class="image"><img src="//martin-thoma.com/captions/queens-moves.png" alt="" style="max-width: 120px; max-height: 120px;" /></a></div></div><div class="gallerytext">Moves of the queen in chess</div></div></li></ul> <h2>isOnBoard(int x, int y)</h2> <p>You should create a method that checks if a coordinate is on your board. This can be as simple as this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">boolean</span> isOnBoard(<span style="color:#339;font-weight:bold">int</span> x, <span style="color:#339;font-weight:bold">int</span> y) { <span style="color:#080;font-weight:bold">return</span> <span style="color:#00D">0</span> &lt;= x &amp;&amp; x &lt; width &amp;&amp; <span style="color:#00D">0</span> &lt;= y &amp;&amp; y &lt; height; } </pre></div> </div> </div> <h2>Diagonal, horizontal and vertical</h2> <p>You can create a method like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">/** * This method checks XYZ and does XYZ. * * @param player the current player * @param xDir -1 if you want to go to the left, 0 if you don't want * to move in x-direction and 1 if you want to go to * the right * @param yDir -1 if you want to go to the bottom, 0 if you don't * want to move in y-direction and 1 if you want to go * to the top */</span> <span style="color:#088;font-weight:bold">private</span> <span style="color:#339;font-weight:bold">void</span> myBoardAction(Player player, <span style="color:#339;font-weight:bold">int</span> xDir, <span style="color:#339;font-weight:bold">int</span> yDir) { <span style="color:#080;font-weight:bold">for</span> (<span style="color:#339;font-weight:bold">int</span> x = <span style="color:#00D">0</span>; x &lt; board.width; x++) { <span style="color:#080;font-weight:bold">for</span> (<span style="color:#339;font-weight:bold">int</span> y = <span style="color:#00D">0</span>; y &lt; board.height; y++) { <span style="color:#080;font-weight:bold">for</span> (<span style="color:#339;font-weight:bold">int</span> c = <span style="color:#00D">0</span>; c &lt; SOME_CONSTANT; c++) { <span style="color:#080;font-weight:bold">if</span> (board.isOnBoard(x + c * xDir, y + c * yDir) &amp;&amp; board.checkXYZ(x + c * xDir, y + c * yDir)) { doXYZ(); } } } } } </pre></div> </div> </div> <p>What’s so special about it? Well, note how the <code>xDir</code> and <code>yDir</code> parameters change the behavior of the method. If you want to move only to the right, you will call <code>myBoardAction(player, 1, 0)</code>. If you want to go to the top left, you will call <code>myBoardAction(player, -1, 1)</code>. Of course, you can’t simply take this piece of code and only change <code>doXYZ()</code> and <code>checkXYZ</code>. You will have to change the starting and and position and maybe add a break. But this thought can be applied to board games quite nice.</p> <p>Please also note that I go from <code>(0|0)</code> to <code>(board.width|board.height)</code> and even add in the inner loop something. So some calls will be out of bound. But because of <a href="http://en.wikipedia.org/wiki/Short-circuit_evaluation">short-circuit evaluation</a> this works. I don’t bother about ends, I simply include the critical parts. Most of the time, it is not much work to check if the call is within the boundary, but finding (and fixing) a bug is much work. Yes, I know, this is more efficient if you use the correct boundaries. But it’s only a constant in time difference. And I guess this constant is very small for most games.</p> <p>Ah, and if you want to check a condition for all diagonals, horizontals and verticals the hole board, you can call it like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>myBoardAction(player, <span style="color:#00D">1</span>, <span style="color:#00D">1</span>); <span style="color:#777">// top right</span> myBoardAction(player,-<span style="color:#00D">1</span>, <span style="color:#00D">1</span>); <span style="color:#777">// top left</span> myBoardAction(player, <span style="color:#00D">1</span>, <span style="color:#00D">0</span>); <span style="color:#777">// vertical</span> myBoardAction(player, <span style="color:#00D">0</span>, <span style="color:#00D">1</span>); <span style="color:#777">// horizontal</span> </pre></div> </div> </div> <p>This is enough. You don’t need more, as you go through the whole board. No need to write redundant code ☺</p> Cyclic references kill Nautilus //martin-thoma.com/cyclic-references-kill-nautilus/ Sun, 20 Jan 2013 21:46:34 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cyclic-references-kill-nautilus <p>I just wanted to answer an assignment and noticed that cyclic references kill Nautilus.</p> <h2>What I did</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">mkdir testFolder <span class="nb">cd </span>testFolder touch testFile.txt ln -s testFile.txt mySoftlink rm testFile.txt ln -s mySoftlink testFile.txt ls -l total 0 lrwxrwxrwx <span class="m">1</span> moose moose <span class="m">10</span> 2013-01-20 21:20 myfile.txt -&gt; mySoftLink lrwxrwxrwx <span class="m">1</span> moose moose <span class="m">10</span> 2013-01-20 21:18 mySoftLink -&gt; myfile.txt</code></pre></div> <p>Those two softlinks refer to each other. Now try to open this folder with Nautilus:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">nautilus /home/moose/Desktop/testFolder/</code></pre></div> <p>Nautilus opens and instantly closes again.</p> <h2>My Nautilus</h2> <p>I use Ubuntu 10.04.4 LTS with Nautilus 2.30.1.</p> <h2>Bug report?</h2> <p>I know, the current version of <a href="http://en.wikipedia.org/wiki/Nautilus_(file_manager)">Nautilus</a> is 3.6.1, but how often do you find a bug which is so easy to reproduce?</p> <p>The Nautilus Bugtracker is <a href="https://bugzilla.gnome.org/browse.cgi?product=nautilus">here</a>, but where would you look for the bug?</p> Wie wende ich die Shannon-Zerlegung an? //martin-thoma.com/wie-wende-ich-die-shannon-zerlegung-an/ Thu, 17 Jan 2013 17:46:27 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-wende-ich-die-shannon-zerlegung-an <p>Die Shannon-Zerlegung ist hilfreich, um die disjunktive bzw. konjunktive Form einer Funktion zu erhalten. Im Folgenden gibt es ein paar Beispiele, wie man das macht:</p> <h2>Vorgehen</h2> <ol> <li>Man hat eine boolsche Funktion `$f(x_1, x_2, \dots, x_n)$` gegeben.</li> <li>Entwickeln nach einer Variablen `$x_i$`: <ol> <li>`$g(x_1, \dots, x_n) := f(x_1, \dots, x_i=1, \dots, x_n)$`</li> <li>`$h(x_1, \dots, x_n) := f(x_1, \dots, x_i=0, \dots, x_n)$`</li> <li>`$f(x_1, x_2, \dots, x_n) = x_i [ g(x_1, \dots, x_n)] \lor \bar x_i [h(x_1, \dots, x_n)]$`</li> </ol> </li> <li>Vereinfachen der Funktion</li> </ol> <h2>Beispiel 1</h2> <p><code>$\begin{align} f(c, b, a) :&amp;= (c \land b) \barwedge a) \Leftrightarrow (b \lor a)\\ \text{Entwickeln nach c:} &amp;= c[((1 \land b) \barwedge a) \Leftrightarrow (b \lor a)] \lor \bar c [((0 \land b) \barwedge a) \Leftrightarrow (b \lor a)]\\ &amp;= c[(b \barwedge a) \Leftrightarrow (b \lor a)] \lor \bar c [(0 \barwedge a) \Leftrightarrow (b \lor a)]\\ &amp;= c[(b \barwedge a) \Leftrightarrow (b \lor a)] \lor \bar c [1 \Leftrightarrow (b \lor a)]\\ &amp;= c((b \barwedge a) \Leftrightarrow (b \lor a)) \lor \bar c (b \lor a)\\ \text{Entwickeln nach b:}&amp;= b \lor \bar b\\ &amp;= b \lor \bar b \\ &amp;= b(c \bar a \lor \bar c) \lor \bar b (ca \lor \bar c a)\\ \text{Entwickeln nach a:} &amp;= a[b(c \bar 1 \lor \bar c) \lor \bar b (c \lor \bar c)] \lor \bar a [b(c \bar 0 \lor \bar c) \lor \bar b (\bar c a)]\\ &amp;=a(b \bar c \lor \bar b) \lor \bar ab\\ &amp;= ab \bar c \lor a \bar b \lor \bar a b\\ &amp;= ab \bar c \lor a \bar b c \lor a \bar b \bar c \lor \bar a b c \lor \bar a b \bar c \end{align}$</code></p> <p>Die letzte Darstellung der Funktion <code>$f$</code> wird Disjunktive Normalform (DNF) genannt. Die vorletzte ist einfach nur eine disjunktion von Konjunktionen.</p> <h2>Beispiel 2</h2> <p><code>$\begin{align} f(c,b,a) &amp;:= ab \lor \bar c\\ \text{Entwickeln nach b:} &amp;= b[a \lor \bar c] \lor \bar b[\bar c]\\ &amp;= b(a \lor \bar c) \lor \bar b \bar c\\ \text{Entwickeln nach a:} &amp;= a[b \lor \bar b \bar c] \lor \bar a [b(\bar c) \lor \bar b \bar c]\\ &amp;= a(b \lor \bar b \bar c) \lor \bar a \bar c\\ &amp;= ab \lor a \bar b \bar c \lor \bar a \bar c\\ &amp;= (abc \lor ab \bar c) \lor a \bar b \bar c \lor (\bar a b \bar c \lor \bar a \bar b \bar c) \end{align}$</code></p> <p>Man muss auch nicht immer Entwicklen, um das Ergebnis zu erhalten. Die Klammern im Ergebnis verdeutlichen, wie man den letzten Schritt durchführt. Also wie man von einer Disjunktiven Form auf die Disjunktive Normalform kommt.</p> Adressierung //martin-thoma.com/adressierung/ Fri, 11 Jan 2013 17:15:56 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/adressierung <div class="info">Dies ist eine Zusammenfassung von mir zu dem Themen Caches, Addressierung und TLB. Ich habe insbesondere bei dem letzem Teil (Cache-Typen und TLBs) das Gef&uuml;hl, dass ich das noch nicht richtig verstanden habe, deshalb ist der Inhalt hier mit Vorsicht zu genie&szlig;en. Bitte meldet mir Fehler oder Unstimmigkeiten (per E-Mail an info@martin-thoma.de oder direkt als Kommentar).</div> <h2 id="allgemeines">Allgemeines</h2> <p>CPU-Caches sind aus Cache-Zeilen aufgebaut. Diese sind die kleinsten adressierbaren Einheiten im Cache. Die Länge der Cache-Zeilen variiert, aber 32-64 Byte sind üblich.<small><sup><a href="#ref1" name="anchor1">[1]</a></sup></small> Nun ist der Cache deutlich kleiner als der Hauptspeicher und man muss eine schnelle Möglichkeit haben, Hauptspeicher-Adressen auf den Cache abzubilden.</p> <p>Eine Möglichkeit das zu machen, ist ein sog. „direct mapped cache“. Das ist im Prinzip eine Hash-Funktion, die zusätlich noch schnell von der Hardware umgesetzt werden können muss. Also unterteilt man gedanklich die Hauptspeicheradressen in 3 Teile:</p> <ul> <li>Tag</li> <li>Index</li> <li>Block-Offset</li> </ul> <p>Der Index gibt direkt die Cache-Zeile an, in der die Daten einer Hauptspeicheradresse landen werden. Es wäre also z.B. möglich, die Pins des Adressbus, auf denen die Index-Bits liegen, auf einen Multiplexer zu legen, der die entsprechende Cache-Zeile durchschaltet.</p> <p>Es gilt also: Index-Länge in Bit = <code>$\log_2(\text{Cache-Zeilen})$</code></p> <p>Nun kann es passieren, dass viele Hauptspeicher-Adressen in der selben Zeile landen. Um diese unterscheiden zu können, speichert man folgendes in einer Cache-Zeile:</p> <ul> <li>Tag</li> <li>Datenblock</li> <li>Flags</li> </ul> <p>Der Datenblock beinhaltet die eigentlichen Daten aus dem Hauptspeicher. Benötigt nun ein Programm die Daten aus einer Hauptspeicheradresse, wird der Index dieser Adresse extrahiert und an dieser Cache-Zeile nachgeschaut. Wenn dann die Tags übereinstimmen, ist es die richtige Adresse und man kann die Daten aus dem Cache entnehmen.</p> <p>Da man durch den Block-Offset ja eine ganze Reihe von Hauptspeicher-Adressen zusammenfasst, muss gelten:</p> <p>Größe der Cache-Zeile <code>$= 2^{\text{Länge des Block-offsets}} \cdot$</code> Größe des Inhalts einer Hauptspeicheradresse</p> <p>Der Block-Offset wird nicht weiter verwendet. Es wird schlicht ignoriert.</p> <p>Der Tag muss aktiv im Cache gespeichert werden und die Länge des Tags im Cache muss mindestens so lang sein wie die Tag-Länge der Hauptspeicher- Adresse. Natürlich wird der Tag im Cache genau so lang sein wie der in der Hauptspeicher-Adresse. Man hat ja keinen Speicher zu verschenken.</p> <p>Bei einem Voll-Assoziativem Cache würde es also keinen Index geben. Eine Hauptspeicher-Adresse würde dann nur in Tag und Block-Offset geteilt werden.</p> <p>Bei einem <code>$n$</code>-fach Satzassoziativem Cache gibt es <code>$\frac{\text{Cachzeilen}}{n}$</code> Sätze mit jeweils <code>$n$</code> Cachezeilen. Das Datenwort kann nur in einem Satz stehen, dort aber an einer beliebigen Stelle. Nun geht die CPU wie folgt vor:</p> <ol> <li>Datenwort mit Hauptspeicheradresse x = `$x_\text{tag}$` | `$x_\text{index}$` | `$x_\text{blockoffset}$` wird ben&ouml;tigt</li> <li>`$x_\text{index}$` = der zu durchsuchende Satz im Cache<br /> Dieser Satz wird zu den `$n$` Vergleichern durchgeschaltet</li> <li>Jeder Vergleicher vergleich den `$x_\text{tag}$` und den in der Cache-Zeile gespeicherten tag</li> <li>Wird die Adresse gefunden &rarr; Cache Hit<br /> Datenwort in keiner Cache-Zeile: Cache-Miss, Hauptspeicherzugriff</li> </ol> <h2>Physical address and virtual address</h2> <p>Die physische Adresse entspricht dem, womit man den Speicherbaustein anspricht. Nun kann es möglich sein, dass man mehrere RAM-Bausteine hat oder dass das Programm theoretische mehr Speicher braucht als an Hauptspeicher zur verfügung steht. Dennoch will man als Programmierer einheitlich adressieren. Also nutzt man im Userspace virtuelle Adressen (Im Kernel-Space können sowohl physische als auch virtuelle Adressen genutzt werden, siehe <a href="http://stackoverflow.com/a/6261020/562769">StackOverflow</a>). Außerdem will man Speicherschutz herstellen. Die virtuellen Adressen sind scheinbar zusammenhängend und der Adressraum ist sehr groß. Der virtuelle Adressraum ist in Blöcke (Pages) unterteilt und die Pages werden von langsamen, aber großen auf schnelle, aber kleine Speichermedien je nach Bedarf aus- oder eingelagert.</p> <p>Das passiert allerdings selten. Um zu sehen, wie häufig das der Fall ist, sollte man sich folgendes anschauen:</p> <ul> <li>/proc/swaps</li> <li>/proc/meminfo - ein paar <a href="http://www.centos.org/docs/5/html/5.2/Deployment_Guide/s2-proc-meminfo.html">Erkl&auml;rungen zu meminfo</a></li> <li><code>vmstat -s</code></li> </ul> <h2 id="cache-modelle">Cache-Modelle</h2> <p>Fordert nun ein Prozess die Daten einer virtuellen Adresse an, kommt es nun auf die verschiedenen Cache-Modelle (PIPT, VIPT, VIVIT) an. Es gilt jedoch immer: Die CPU schaut im TLB nach, ob sie direkt erfahren kann, wo die Daten sind. Falls das nicht funktiniert, geht es wie folgt weiter:</p> <h3 id="physically-indexed-physically-tagged">Physically Indexed, Physically Tagged</h3> <p>Hier wird der index und der tag aus der physischen Adresse gezogen. Damit muss zuerst die MMU die virtuelle Adresse in eine physische Adresse umwandeln, bevor man im Cache nachschauen kann.</p> <h3 id="virtually-indexed-physically-tagged">Virtually indexed, physically tagged</h3> <p>Man bekommt den Index aus der virtuellen Adresse, kann im Cache nachschauen ob dort überhaupt etwas steht, falls ja muss aber noch die MMU die physische Adresse nachschlagen damit man den tag überprüfen kann.</p> <div class="frage">Frage: Wieso steht in den Folien "No ambiguities"?<br />Annahme: Wir haben eine virtuelle Adresse 123456789. Der Index sind die Ziffern [4,6] also 456. Nun wird das auf die physische Adresse 123456789 gemappt. Der Tag sind die Ziffern [1,3] also 123.<br />Nun haben wir eine zweite virtuelle Adresse 000456000. Der index sind die Ziffern [4,6] also 456. Die zugeh&ouml;rige phyische Adresse sein 123000000. Der Tag sind die Ziffern [1,3] also 123.<br />Nun m&uuml;sste doch fehlerhaft ein Cache-Hit herauskommen, oder?</div> <h3 id="physically-indexed--virtually-tagged">Physically Indexed / Virtually Tagged</h3> <p>Macht keinen Sinn, weil man Probleme wegen Doppeldeutigkeiten bekommen kann und man auf jeden Fall immer zuerst die MMU nutzen kann.</p> <h3 id="virtually-indexed--virtually-tagged">Virtually Indexed / Virtually Tagged</h3> <p>Kein MMU-Zugriff benötigt, also schneller als die anderen Varianten. Birgt aber ein paar Probleme (Ambiguity, Alias)</p> <h2 id="quellen">Quellen</h2> <p>[^1] <a href="http://alasir.com/articles/cache_principles/cache_line_tag_index.html">Functional Principles of Cache Memory</a></p> <ul> <li><a href="http://people.cs.umass.edu/~emery/classes/cmpsci377/current/notes/lecture_15_vm.pdf">Page-Table Lookups</a></li> <li><a href="http://de.wikipedia.org/wiki/Virtuelle_Adresse#Motivation">Virtuelle Adresse</a></li> <li><a href="http://en.wikipedia.org/wiki/CPU_cache">CPU cache</a></li> <li><a href="http://lwn.net/Articles/106177/">Four-level page tables</a></li> <li><a href="http://bottomupcs.sourceforge.net/csbu/x2816.htm">Linux Specifics: Address Space Layout</a></li> <li><a href="http://www.ecst.csuchico.edu/~hilzer/csci152/htm/EAT-TLB.htm">Some example assignments</a> (Memory access times, With and without TLBs)</li> </ul> How to sort with Java //martin-thoma.com/how-to-sort-with-java/ Tue, 08 Jan 2013 21:49:47 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-sort-with-java <p>Sorting is a very basic task that every programmer should be able to solve. In Python, you have sort and sorted. In C++, you can use <a href="../cpp-operator-overloading/#Sorting">operator overloading</a>. I’ll now tell you how to do basic sorting with Java. I will not write about <a href="http://www.codinghorror.com/blog/2007/12/sorting-for-humans-natural-sort-order.html">natural language sorting</a> or language-aware sorting. This is only about simple sorting with Java.</p> <h2>Sorting without programming</h2> <p>First of all, you have to make sure that you understand how sorting works - without Java, just in the real world.</p> <p>What you need:</p> <ul> <li>A container `$C$` of objects</li> <li>A way to compare two objects of the list at a time. The comparison, lets call it `$\leq$` needs to satisfy the following conditions: <ul> <li><a href="http://en.wikipedia.org/wiki/Total_relation">totality</a>: `$\forall x, y \in C: x \leq y \lor y \leq x$`</li> <li><a href="http://en.wikipedia.org/wiki/Antisymmetric_relation">antisymmetry</a>: `$\forall x,y \in C: x \leq y \land y \leq x \Rightarrow x = y$`</li> <li><a href="http://en.wikipedia.org/wiki/Transitive_relation">transitivity</a>: `$\forall x,y,z \in C: x \leq y \land y \leq z \Rightarrow x \leq z$`</li> </ul> </li> </ul> <p>Just think about what you sort in your everyday life:</p> <ul> <li>Numbers</li> <li>Words</li> <li><a href="http://en.wikipedia.org/wiki/List_of_countries_by_population">Contries by population</a></li> <li>Playing cards</li> </ul> <p>You can apply different algorithms like <a href="http://en.wikipedia.org/wiki/Selection_sort">selection sort</a> which you would use for numbers or <a href="http://en.wikipedia.org/wiki/Insertion_sort">insertion sort</a> which you would use for card games. No matter what algorithm you use, you need to be able to compare the elements.</p> <p>Note that you can compare some objects, like countries, by many measures. You could look at the population, the birth rate or the area. No matter what you use to compare, the this will not influence the way you sort.</p> <h2>Collections</h2> <p>One way to sort is to implement the interface <a href="http://docs.oracle.com/javase/7/docs/api/java/util/List.html">List</a>. For all datastructures, that implement the interface List or one of its sub-interfaces you can use <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Collections.html">Collections</a> an go on like this:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.Collections</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.LinkedList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Main</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">String</span><span class="o">&gt;</span> <span class="n">myList</span> <span class="o">=</span> <span class="k">new</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">String</span><span class="o">&gt;();</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="s">&quot;I&quot;</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="s">&quot;think&quot;</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="s">&quot;therefore&quot;</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="s">&quot;I&quot;</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="s">&quot;am&quot;</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">myList</span><span class="o">);</span> <span class="n">Collections</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">myList</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">myList</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="o">[</span>I, think, therefore, I, am<span class="o">]</span> <span class="o">[</span>I, I, am, therefore, think<span class="o">]</span></code></pre></div> <p>Note that I didn’t write a Comparator or implement Comparable as String has one by default. Don’t mix <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Collections.html">Collections</a> and <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Collection.html">Collection</a>! A Set is a Collection, but it is not sortable. Collections is a class that you can use for sorting. Like <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Math.html">Math</a>, that has utilities like <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Math.html#sqrt(double)">sqrt</a></p> <h2>Arrays</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.Arrays</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Main</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">String</span><span class="o">[]</span> <span class="n">myStrings</span> <span class="o">=</span> <span class="k">new</span> <span class="n">String</span><span class="o">[</span><span class="mi">5</span><span class="o">];</span> <span class="n">myStrings</span><span class="o">[</span><span class="mi">0</span><span class="o">]</span> <span class="o">=</span> <span class="s">&quot;I&quot;</span><span class="o">;</span> <span class="n">myStrings</span><span class="o">[</span><span class="mi">1</span><span class="o">]</span> <span class="o">=</span> <span class="s">&quot;think&quot;</span><span class="o">;</span> <span class="n">myStrings</span><span class="o">[</span><span class="mi">2</span><span class="o">]</span> <span class="o">=</span> <span class="s">&quot;therefore&quot;</span><span class="o">;</span> <span class="n">myStrings</span><span class="o">[</span><span class="mi">3</span><span class="o">]</span> <span class="o">=</span> <span class="s">&quot;I&quot;</span><span class="o">;</span> <span class="n">myStrings</span><span class="o">[</span><span class="mi">4</span><span class="o">]</span> <span class="o">=</span> <span class="s">&quot;am&quot;</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">Arrays</span><span class="o">.</span><span class="na">asList</span><span class="o">(</span><span class="n">myStrings</span><span class="o">));</span> <span class="n">Arrays</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">myStrings</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">Arrays</span><span class="o">.</span><span class="na">asList</span><span class="o">(</span><span class="n">myStrings</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Interface Comparable</h2> <p>This is an example how you could implement <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Comparable.html">Comparable</a>.</p> <p>Country.java</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">Country</span> <span class="kd">implements</span> <span class="n">Comparable</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">population</span><span class="o">;</span> <span class="kt">double</span> <span class="n">area</span><span class="o">;</span> <span class="n">String</span> <span class="n">name</span><span class="o">;</span> <span class="kd">public</span> <span class="nf">Country</span><span class="o">(</span><span class="kt">int</span> <span class="n">population</span><span class="o">,</span> <span class="kt">double</span> <span class="n">area</span><span class="o">,</span> <span class="n">String</span> <span class="n">name</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">population</span> <span class="o">=</span> <span class="n">population</span><span class="o">;</span> <span class="k">this</span><span class="o">.</span><span class="na">area</span> <span class="o">=</span> <span class="n">area</span><span class="o">;</span> <span class="k">this</span><span class="o">.</span><span class="na">name</span> <span class="o">=</span> <span class="n">name</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">compareTo</span><span class="o">(</span><span class="n">Country</span> <span class="n">o</span><span class="o">)</span> <span class="o">{</span> <span class="c1">// a negative integer, zero, or a positive integer as this</span> <span class="c1">// object is less than, equal to, or greater than the</span> <span class="c1">// specified object.</span> <span class="k">return</span> <span class="k">this</span><span class="o">.</span><span class="na">name</span><span class="o">.</span><span class="na">compareTo</span><span class="o">(</span><span class="n">o</span><span class="o">.</span><span class="na">name</span><span class="o">);</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="n">String</span> <span class="nf">toString</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">name</span> <span class="o">+</span> <span class="s">&quot;: &quot;</span> <span class="o">+</span> <span class="n">population</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Main.java</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.Collections</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Main</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;</span> <span class="n">europe</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;();</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">82000000</span><span class="o">,</span><span class="mi">350000</span><span class="o">,</span><span class="s">&quot;Germany&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">60000000</span><span class="o">,</span><span class="mi">360000</span><span class="o">,</span> <span class="s">&quot;France&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">20000000</span><span class="o">,</span><span class="mi">100000</span><span class="o">,</span> <span class="s">&quot;Norway&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">30000000</span><span class="o">,</span><span class="mi">500000</span><span class="o">,</span> <span class="s">&quot;Sweden&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">50000000</span><span class="o">,</span><span class="mi">123000</span><span class="o">,</span> <span class="s">&quot;Spain&quot;</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">Collections</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="o">[</span>Germany: 81903000, France: 64667000, Norway: 4985900, Sweden: 9514406, Spain: 47212990, Switzerland: 8014000, Monaco: 36371<span class="o">]</span> <span class="o">[</span>France: 64667000, Germany: 81903000, Monaco: 36371, Norway: 4985900, Spain: 47212990, Sweden: 9514406, Switzerland: 8014000<span class="o">]</span></code></pre></div> <p>You should definitely add JavaDoc and comment what you’ve compared. Note that it would sort the list in reverse order if you switched <code>this.population - o.population;</code> to <code>o.population - this.population;</code>. This would be bad style, as the JavaDoc of Comparable define the order. If you would like to sort in reverse, you should use <code>Collections.reverse(europe);</code>.</p> <p>You can also use compareTo() within compareTo():</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">compareTo</span><span class="o">(</span><span class="n">Country</span> <span class="n">o</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="k">this</span><span class="o">.</span><span class="na">name</span><span class="o">.</span><span class="na">compareTo</span><span class="o">(</span><span class="n">o</span><span class="o">.</span><span class="na">name</span><span class="o">);</span> <span class="o">}</span></code></pre></div> <h2>Comparator</h2> <p>If you need to compare objects in multiple ways, you might need to implement <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Comparator.html#compare(T, T)">Comperator</a>. If you only have to compare objects in one way, I would always use the Interface Comparable. It’s easier to use.</p> <h3>External Comparator</h3> <p>An external Comparator PopulationDensityComperator.java could look like this:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.Comparator</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">PopulationDensityComperator</span> <span class="kd">implements</span> <span class="n">Comparator</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;</span> <span class="o">{</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">compare</span><span class="o">(</span><span class="n">Country</span> <span class="n">o1</span><span class="o">,</span> <span class="n">Country</span> <span class="n">o2</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">o1Density</span> <span class="o">=</span> <span class="n">o1</span><span class="o">.</span><span class="na">population</span> <span class="o">/</span> <span class="n">o1</span><span class="o">.</span><span class="na">area</span><span class="o">;</span> <span class="kt">double</span> <span class="n">o2Density</span> <span class="o">=</span> <span class="n">o2</span><span class="o">.</span><span class="na">population</span> <span class="o">/</span> <span class="n">o2</span><span class="o">.</span><span class="na">area</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">o1Density</span> <span class="o">-</span> <span class="n">o2Density</span><span class="o">)</span> <span class="o">&lt;</span> <span class="mf">0.00001</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">0</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="k">return</span> <span class="n">o1Density</span> <span class="o">-</span> <span class="n">o2Density</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>and you would use it like this in the Main.java:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.Collections</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Main</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;</span> <span class="n">europe</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;();</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">81903000</span><span class="o">,</span><span class="mf">357121.41</span><span class="o">,</span><span class="s">&quot;Germany&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">64667000</span><span class="o">,</span><span class="mi">668763</span><span class="o">,</span> <span class="s">&quot;France&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">4985900</span><span class="o">,</span><span class="mi">385199</span><span class="o">,</span> <span class="s">&quot;Norway&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">9514406</span><span class="o">,</span><span class="mi">450295</span><span class="o">,</span> <span class="s">&quot;Sweden&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">47212990</span><span class="o">,</span><span class="mi">504645</span><span class="o">,</span> <span class="s">&quot;Spain&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">8014000</span><span class="o">,</span> <span class="mi">41285</span><span class="o">,</span> <span class="s">&quot;Switzerland&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">36371</span><span class="o">,</span> <span class="mf">2.02</span><span class="o">,</span> <span class="s">&quot;Monaco&quot;</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">Collections</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">Collections</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">europe</span><span class="o">,</span> <span class="k">new</span> <span class="nf">PopulationDensityComperator</span><span class="o">());</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Your output would be:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="o">[</span>Germany: 81903000, France: 64667000, Norway: 4985900, Sweden: 9514406, Spain: 47212990, Switzerland: 8014000, Monaco: 36371<span class="o">]</span> <span class="o">[</span>France: 64667000, Germany: 81903000, Monaco: 36371, Norway: 4985900, Spain: 47212990, Sweden: 9514406, Switzerland: 8014000<span class="o">]</span> <span class="o">[</span>Norway: 4985900, Sweden: 9514406, Spain: 47212990, France: 64667000, Switzerland: 8014000, Germany: 81903000, Monaco: 36371<span class="o">]</span></code></pre></div> <h3>Internal (anonymous) Comparator</h3> <p>You can also directly implement the comperator where you need it:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.Collections</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.Comparator</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Main</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;</span> <span class="n">europe</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;();</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">81903000</span><span class="o">,</span><span class="mf">357121.41</span><span class="o">,</span><span class="s">&quot;Germany&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">64667000</span><span class="o">,</span><span class="mi">668763</span><span class="o">,</span> <span class="s">&quot;France&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">4985900</span><span class="o">,</span><span class="mi">385199</span><span class="o">,</span> <span class="s">&quot;Norway&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">9514406</span><span class="o">,</span><span class="mi">450295</span><span class="o">,</span> <span class="s">&quot;Sweden&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span><span class="mi">47212990</span><span class="o">,</span><span class="mi">504645</span><span class="o">,</span> <span class="s">&quot;Spain&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">8014000</span><span class="o">,</span> <span class="mi">41285</span><span class="o">,</span> <span class="s">&quot;Switzerland&quot;</span><span class="o">));</span> <span class="n">europe</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="k">new</span> <span class="nf">Country</span><span class="o">(</span> <span class="mi">36371</span><span class="o">,</span> <span class="mf">2.02</span><span class="o">,</span> <span class="s">&quot;Monaco&quot;</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">Collections</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="n">Collections</span><span class="o">.</span><span class="na">sort</span><span class="o">(</span><span class="n">europe</span><span class="o">,</span> <span class="k">new</span> <span class="n">Comparator</span><span class="o">&lt;</span><span class="n">Country</span><span class="o">&gt;(){</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">compare</span><span class="o">(</span><span class="n">Country</span> <span class="n">o1</span><span class="o">,</span> <span class="n">Country</span> <span class="n">o2</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">o1Density</span> <span class="o">=</span> <span class="n">o1</span><span class="o">.</span><span class="na">population</span> <span class="o">/</span> <span class="n">o1</span><span class="o">.</span><span class="na">area</span><span class="o">;</span> <span class="kt">double</span> <span class="n">o2Density</span> <span class="o">=</span> <span class="n">o2</span><span class="o">.</span><span class="na">population</span> <span class="o">/</span> <span class="n">o2</span><span class="o">.</span><span class="na">area</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">o1Density</span> <span class="o">-</span> <span class="n">o2Density</span><span class="o">)</span> <span class="o">&lt;</span> <span class="mf">0.00001</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">0</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="nf">if</span> <span class="o">(</span><span class="n">o1Density</span> <span class="o">&gt;</span> <span class="n">o2Density</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">1</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="k">return</span> <span class="o">-</span><span class="mi">1</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span> <span class="o">});</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">europe</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Your output would be:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="o">[</span>Germany: 81903000, France: 64667000, Norway: 4985900, Sweden: 9514406, Spain: 47212990, Switzerland: 8014000, Monaco: 36371<span class="o">]</span> <span class="o">[</span>France: 64667000, Germany: 81903000, Monaco: 36371, Norway: 4985900, Spain: 47212990, Sweden: 9514406, Switzerland: 8014000<span class="o">]</span> <span class="o">[</span>Norway: 4985900, Sweden: 9514406, Spain: 47212990, France: 64667000, Switzerland: 8014000, Germany: 81903000, Monaco: 36371<span class="o">]</span></code></pre></div> <p>I don’t recommend this way for some reasons:</p> <ul> <li>It is more likely that your code gets more difficult to read</li> <li>It's more difficult to reuse your code (you can't use the same Comparator in another location)</li> <li>It's more difficult to extend your code</li> </ul> <p>An argument for such an Comparator might be, that it is easier to read. But this is only an argument if the Comparator is very short.</p> <h2>More examples</h2> <ul> <li>StackOverflow: <a href="http://stackoverflow.com/q/3718383/562769">java class implements comparable</a></li> </ul> Web Engineering //martin-thoma.com/web-engineering/ Thu, 03 Jan 2013 13:57:06 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/web-engineering <div class="info">Dieser Artikel besch&auml;ftigt sich mit der Vorlesung &bdquo;Web Engineering&ldquo; am KIT. Er dient als Pr&uuml;fungsvorbereitung. Ich habe Web Engineering bei Dr. Nussbaumer geh&ouml;rt.</div> <h2>&Uuml;ber die Vorlesung</h2> <p>In der Vorlesung „Web Engineering“ lernt man, welche besonderen Herausforderungen Web-Projekte beinhalten und wie man damit umgehen kann. Es wird zwar auch über technische Aspekte geredet (siehe Part 1), aber es geht vor allem um Projektplanung und -management. Insbesondere wird hier nichts konkret entwickelt. Dafür gibt es vermutlich das Praktikum, das aber unabhängig von der Vorlesung ist.</p> <p>Herr Dr. Nussbaumer hält die Vorlesung sehr interaktiv. Er stellt viele Fragen, über die man in der Vorlesung diskutieren kann und ist auch immer nach der Vorlesung bereit etwas genauer zu erklären.</p> <p>Die Struktur unter „Vorbereitung“ richtet sich nach dem Aufbau der Folien.</p> <h2>Vorbereitung</h2> <p>Prüfungsprotokolle sind bei der <a href="http://www.fsmi.uni-karlsruhe.de/Studium/Pruefungsprotokolle/">Fachschaft Informatik</a> zu erhalten. <a href="../images/2013/01/muendlich-we-2013-martin-thoma.pdf">Mein Prüfungsprotokoll</a> ist hier und die <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/kit-muendlich-info">TeX-Quelldateien</a> bekommt ihr natürlich auch.</p> <p>Im Folgenden sind einige Stichpunkte aufgelistet, die jedem etwas sagen sollten.</p> <h3>Geschichte</h3> <ul> <li>1945: <a href="http://de.wikipedia.org/wiki/Vannevar_Bush">Vannevar Bush</a>, <a href="http://de.wikipedia.org/wiki/Memex">Memex</a></li> <li>1965: <a href="http://de.wikipedia.org/wiki/Ted_Nelson">Ted Nelson</a>, Hypertext und Xanadu</li> <li>1969: ARPANET</li> <li>1985: Bill Atkinson (Apple), <a href="http://www.youtube.com/watch?v=BeMRoYDc2z8">HyperCard</a></li> <li>1989: Tim Berners-Lee, World Wide Web</li> <li>1993: <a href="http://de.wikipedia.org/wiki/NCSA_Mosaic">Mosaic</a></li> </ul> <h3>PART 1: Technologies</h3> <ul> <li>Markup, HTML, Ressources, Cookies, <abbr title="Multipurpose Internet Mail Extensions"><a href="http://de.wikipedia.org/wiki/MIME-Type">MIME</a></abbr></li> <li>Host, Server, Client, User Agent</li> <li>Hypertext Paradigm</li> <li>HTTP, HTTPS, FTP, SMTP, UDDI</li> <li>CGI</li> <li><a href="http://de.wikipedia.org/wiki/SOAP">SOAP</a>, <a href="http://de.wikipedia.org/wiki/WebDAV">WebDAV</a></li> <li>Moore's Law, Nielson's Law</li> <li>Was ist der Unterschied zwischen Software Engineering und Web Engineering? &rarr; Antwort auf Folie 47ff, part0-1</li> <li><a href="http://de.wikipedia.org/wiki/Paretoprinzip">Paretoprinzip</a></li> <li>Was ist das W3C? Was sind die Ziele des W3C? Wer ist Teil des W3C?</li> <li><a href="http://de.wikipedia.org/wiki/Zonendatei">Zone File</a></li> <li>Uniform addressing &rarr; Was ist das?</li> <li>URI, URL, URN, URC, RFC1630</li> </ul> <h3>PART 2: Project Management</h3> <ul> <li><a href="http://de.wikipedia.org/wiki/Chaos-Studie">Chaos-Report</a> der Standish Group (25%, 45%, 30%) <ul> <li>Bad: Very high budget</li> <li>Good: Executive Management, User Involvement, Experienced Project Manager, Clear Business Objectives, Minimizing Scope, Requirements Process, Standard Software Infrastructure, Formal Methology, Reliable Estimates, Skilled Staff</li> <li>&bdquo;When projects fail, it's rarely technical.&ldquo;</li> </ul> </li> <li>Outsource, Find&amp;Buy, Develop new solution</li> </ul> <p><strong>Teams:</strong></p> <ul> <li>&lt; 6 Entwickler</li> <li>&lt; 6 Monate</li> <li><abbr title="Release early, release often">RERO</abbr></li> <li>Verantwortungsbereiche: <ul> <li>Product Management: Wie verkaufe ich die Software?</li> <li>Program Management: Wie bringe ich das Projekt zu einem erfolgreichem Abschluss?</li> <li>Architekture: Wie halte ich die Software erweiterbar, anpassbar und wartbar?</li> <li>Development: Wie schreibe ich den Code von Methode abc in Klasse xyz?</li> <li>Test: Sind alle funktionalen und qualitativen Anforderungen erf&uuml;llt? Ist das System robust?</li> <li>User Experience: Passiert das, was der Nutzer erwartet? Kann man dem User die Bedienung der Software erleichtern?</li> <li>Release / Operations: Wie halte ich die Software &uuml;ber Jahre am laufen?</li> </ul> </li> <li>Aufsplitten der Teams nach Funktionen oder Features <ul> <li>Wo ist der Unterschied?</li> </ul> </li> </ul> <p><strong>Tasks &amp; Tools</strong></p> <ul> <li><a href="http://de.wikipedia.org/wiki/Work_Breakdown_Structure">Work Breakdown Structure</a></li> <li>GANTT chart</li> <li><a href="http://de.wikipedia.org/wiki/Program_Evaluation_and_Review_Technique">PERT</a></li> <li><a href="http://en.wikipedia.org/wiki/SWOT_analysis">SWOT Analysis</a></li> </ul> <p><strong>Risiken</strong></p> <ul> <li>Cost-reduction expectations</li> <li>Data security / protection (IPR)</li> <li>Process discipline (Was ist das?)</li> <li>Loss of business knowledge</li> <li>Vendor failure to deliver</li> <li>Scope creep</li> <li>Government oversight / regulation</li> <li>Culture (language and callcenters)</li> <li>Turnover of key personnel</li> <li>Knowledge transfer</li> </ul> <p><strong>Process Models</strong></p> <ul> <li><a href="http://en.wikipedia.org/wiki/Code_and_fix#Code_and_fix">Code and fix</a></li> <li>Waterfall model</li> <li>Prototyping model</li> <li>Evolutionary Development model: Only for small, scientific projects where project goal is unclear</li> <li>Spiral model: Risk-driven</li> <li><abbr title="Rational Unified Process model">RUP</abbr> von SAP</li> <li><abbr title="Microsoft Solution Framework">MSF</abbr> &rarr; <a href="http://msdn.microsoft.com/de-de/library/bb979125.aspx">msdn Artikel</a> <ul> <li>Rollen: <ul> <li>Product Management: Anwalt des Kunden, team&uuml;bergreifende Projekt-Vision, betriebswirtschaftliche Sicht auf das Projekt</li> <li>Program Management: &bdquo;Projektleiter&ldquo;, Teamkommunikation, technische Sicht auf das Projekt</li> <li>Architecture, Development, Testing, Release / Operations</li> <li>User Experience: Anwalt des Benutzers</li> </ul> </li> <li>Skalierung: Feature-Teams vs. Functional Teams</li> <li>Meilensteine: Extern sichtbare und Interim-Meilensteine</li> </ul> </li> <li>Reuse-Oriented Approaches</li> <li>Agile Methoden: <ul> <li>Scrum: <ul> <li>Rollen: Scrum Master, Product Owner, Development Team</li> <li>Iterations, Sprints, User Stories</li> <li><a href="http://if-blog.de/scrum-plakat">Scrum Plakat</a></li> <li><a href="http://www.youtube.com/watch?v=r6brn76hDec">Video: What is Scrum?</a>, <a href="http://www.youtube.com/watch?v=XU0llRltyFM#t=32s">Scrum in 8 minutes</a>, <a href="http://refcardz.dzone.com/refcardz/scrum">Scrum Refcard</a>, <a href="http://sendspace.com/pro/dl/qh5zug">Scrum Master Checklist</a></li> </ul> </li> <li><abbr title="Extreme Programming">XP</abbr>: Paarprogrammierung, <a href="http://www.youtube.com/watch?v=XP4o0ArkP4s">Lecture 24: Richard Buckland</a> (45 minutes)</li> <li><a href="http://agilemanifesto.org/">Agile manifesto</a></li> </ul> </li> </ul> <h3>PART 3: Requirements Engineering</h3> <ul> <li>Ablauf: <ol> <li>Initiate: Project Charter, Identify business opportunity, gather business requirements, <abbr title="target customer">FOR</abbr> WHO <abbr title="product name">THE</abbr> <abbr title="product category">IS</abbr> <abbr title="key benefit">THAT</abbr> <abbr title="primary competition">UNLIKE</abbr> <abbr title="primary difference">OUR PRODUCT</abbr></li> <li>Elicitation: Refine requirements (Busines requirements, functional requirements, non-functional requirements), Coopers Persona-Ansatz (<a href="http://de.wikipedia.org/wiki/Persona_(Mensch-Computer-Interaktion)#Beispiel">Beispiele</a>)</li> <li>Asses: Understand and organize requirements, features and feature sets</li> <li>Specification: <a href="http://en.wikipedia.org/wiki/Software_Requirements_Specification">Software requirements specification</a></li> <li>Validation</li> </ol> </li> <li>Gather requirements (Interviewing, <a href="http://en.wikipedia.org/wiki/Job_shadowing">Shadowing</a>, surveys, brainstorming, user instructions - z.B. bei Atomkraftwerken gibt es wohl schon Prozessabl&auml;ufe)</li> <li><a href="http://dropsafe.crypticide.com/article/1006">A11Y, L10N, I18N, G11N</a>: <a href="http://de.wikipedia.org/wiki/BITV">BITV</a></li> <li>RNA: Relationship-Navigation Analysis</li> <li><a href="http://de.wikipedia.org/wiki/Web_Accessibility_Initiative">WAI</a></li> </ul> <h3>PART 4: Entwurf</h3> <p>Logischer Entwurf (Abstrakt: Wireframes, Navigation patterns) ↔ Physikalischer Entwurf (Konkret: UI Frameworks, Services)</p> <h4>Content Management Aspects</h4> <ul> <li>Content-Typen m&uuml;ssen definiert werden, um Inhalte von der Darstellung trennen zu k&ouml;nnen</li> <li>Content-Typen sind auch f&uuml;r die Suche relevant</li> <li>Templates m&uuml;ssen erstellt werden</li> <li>Welche Metadaten liegen vor?</li> <li>Wie k&ouml;nnen Metadaten weitergegeben werden? &rarr; <a href="http://support.google.com/webmasters/bin/answer.py?hl=en&amp;answer=99170">Rich Snippets</a></li> <li>Welche <abbr title="Denglisch: Workflows">Arbeitsabl&auml;ufe</abbr> habe ich?</li> <li>Inhalt kann in flachen/strukturierten Dateien oder in Datenbanken liegen.</li> <li>Strukturierte Dateien: XML, RDF (&rarr; <a href="http://www.youtube.com/watch?v=ldl0m-5zLz4">Video</a>), Microformats</li> </ul> <h4>Software Interface Aspects</h4> <div class="definition"><em>Usability</em> is the extent to which a product can be used by specified users to achieve specified goals with effectiveness, efficiency and satisfaction in a specified context of use. - ISO 9241-11</div> <div class="definition">User Experience is a person's perception and responses that result from the use or anticipated use of a product, system or service. - ISO 9241-210</div> <ul> <li>User-centered design &rarr; <a href="http://en.wikipedia.org/wiki/User-centered_design">Wiki</a></li> <li>Mentale Modelle: Taschenrechner, Explorer, Start-Vorgang, Einkaufssysteme, Hyperlinks, Tastatur</li> <li>Metaphern</li> <li>User-Modelle: Rollen, Markt-Anteile, Personas</li> </ul> <h4>Hypertext Systm Aspects</h4> <ul> <li>Known-item search / exploratory search</li> </ul> <h4>Business Process Aspects</h4> <p>Kommt noch</p> <h3>Weiteres</h3> <ul> <li><a href="http://en.wikipedia.org/wiki/Web_Services_Description_Language">WSDL</a></li> <li><a href="http://en.wikipedia.org/wiki/Microsoft_Solutions_Framework">MSF</a> vs. <a href="http://en.wikipedia.org/wiki/Scrum_(development)">Scrum</a> - <a href="http://pm.stackexchange.com/a/8493/5195">Roles in Scrum</a></li> <li><a href="http://en.wikipedia.org/wiki/Hypertext_Transfer_Protocol">HTTP</a></li> </ul> <h3>Weitere Informationen</h3> <p>Folgende Artikel sollte man lesen:</p> <ul> <li><a href="http://de.wikipedia.org/wiki/Internet">Internet</a></li> <li><a href="http://de.wikipedia.org/wiki/Geschichte_des_Internets">Geschichte des Internets</a></li> <li><a href="http://de.wikipedia.org/wiki/Chronologie_des_Internets">Chronologie des Internets</a></li> </ul> <p>Diese Tutorials sollte man machen:</p> <ul> <li><a href="http://www.w3schools.com/xml/xml_whatis.asp">XML Tutorial</a> - <a href="http://www.w3schools.com/quiztest/quiztest.asp?qtest=XML">XML Quiz</a></li> <li><a href="http://www.w3schools.com/soap/soap_intro.asp">SOAP Tutorial</a></li> </ul> <h2>Typische Fragen</h2> <div class="question"> <span class="question">Was ist Web Engineering?</span> <div class="answer"> <ul> <li>It's not science, and it isn't exactly engineering, either.</li> <li>Disziplin aus Disziplinen (Software Engineering, Hypermedia, Information Systems, Network Engineering)</li> <li>Teilweise ist es wie Software Engineering (Requirements engineering, reproduzierbare Erfolge durch strukturierte Herangehensweise), teilweise hat es typische Problemquellen, die im Software Engineering weniger verbreitet sind (Skalierbarkeit, Load balancing, Hypermedia).</li> </ul> </div> </div> <div class="question"> <span class="question">Was ist eine Ressource?</span> <div class="answer">Eine Ressource ist ein Objekt, dass von einem Webserver oder Websystem mittels eines standardisierten Protokolls ausgeliefert wird und durch einen MIME-Typen spezifiziert wird.</div> </div> <div class="question"> <span class="question">Wie werden Ressourcen adressiert?</span> <div class="answer">Durch URIs, meist URLs aber auch URNs.</div> </div> <div class="question"> <span class="question">Was ist ein Webservice?</span> <div class="answer">Ein Webservice ist eine Software-Anwendung, die mit einem URI eindeutig identifizierbar ist und deren Schnittstelle als XML-Artefakt definiert, beschrieben und gefunden werden kann. Diese Schnittstelle kann mit WSDL beschrieben werden. </div> </div> <div class="question"> <span class="question">Was ist das Endpoint-ABC?</span> <div class="answer"> Wurde durch die WCF gepr&auml;gt und ist <a href="http://stackoverflow.com/q/8893128/562769">z.B. so in der Web.config</a>. Das ABC steht f&uuml;r ... <ul> <li>Address (Wo ist der Endpoint?)</li> <li>Binding (Wie verbinde ich? Protokoll? Encoding?)</li> <li>Contract (Welche Informationen will ich &uuml;bertragen?)</li> Siehe auch: <a href="http://fczaja.blogspot.de/2010/10/wcf-endpoint-abc.html">Filip's Technical Blog</a> <div class="question"> <span class="question">Welche Ziele verfolgt das W3C?</span> <div class="answer"> <ul> <li>Web for Everyone</li> <li>Web on Everything</li> <li>Knowledge Base</li> <li>Trust and Confidence</li> </ul> </div> </div> <div class="question"> <span class="question">Wie ist der Arbeitsprozess beim W3C?</span> <div class="answer"> Workshops &rarr; Notes from members &rarr; Briefing package with membership vote &rarr; Requirements Document &rarr; Working Draft &rarr; Candidate Recommendation &rarr; Proposed Recommendation &rarr; W3C Recommendation (<a href="http://en.wikipedia.org/wiki/W3C_recommendation">source</a>) </div> </div> <h2>Interessante Fragen</h2> <div class="question"> <span class="question">Vergleichen Sie RPCs und Web Services</span> <div class="answer"> <ul> <li>Web Services sind leichter skalierbar.</li> </ul> (Siehe auch: <a href="http://stackoverflow.com/a/1350982/562769">StackOverflow</a>) </div> </div> <div class="question"> <span class="question">Wie l&auml;uft ein HTTP-Request ab?</span> <div class="answer">Siehe <a href="http://www.tecchannel.de/netzwerk/management/401210/hypertext_transfer_protocol/index2.html">TechChannel.de</a> </div> </div> <h2>Hintergrundwissen</h2> <a href="http://igoro.com/archive/what-really-happens-when-you-navigate-to-a-url/">What really happens when you navigate to a URL</a> <ul> <li><a href="http://stackoverflow.com/a/11021207/562769">OS-DNS-Cache on Linux</a></li> <li><a href="http://superuser.com/a/31691/64857">What exactly happens when you browse a website in your browser?</a> (fun to read)</li> <li><a href="http://stackoverflow.com/a/2092602/562769">What happens when you type in a URL in browser?</a> (well structured)</li> </ul> <h2>Termine</h2> Web Engineering wird m&uuml;ndlich gepr&uuml;ft. Dazu muss man sich bei Herrn Matthias Keller (matthias.keller@kit.edu) melden und einen Termin ausmachen. Zus&auml;tzlich muss man sich &uuml;ber QISPOS anmelden. <strong>Datum</strong>: Dienstag, der 19. Februar 2013 um 14:30 Uhr (individuell, siehe Organisation) <strong>Ort</strong>: Geb. 20.21 (SCC), Raum 303 (individuell, siehe Organisation) <strong>Dauer</strong>: 15 Minuten <strong>Punkte</strong>: 4 ECTS </ul></div></div> Disable Wikipedia fundraising banner //martin-thoma.com/disable-wikipedia-fundraising-banner/ Wed, 02 Jan 2013 15:10:34 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/disable-wikipedia-fundraising-banner <p>I didn’t spend this year for Wikipedia because of the advertising. It really got on my nerves:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/wikipedia-advertising-300x85.png"><img src="../images/2013/01/wikipedia-advertising-300x85.png" alt="Wikipedia advertising - Fundraising campaign" width="" height="" class="size-medium wp-image-53041" /></a><p class="wp-caption-text">Wikipedia advertising - Fundraising campaign</p></div> <p>But you can simply disable it:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2013/01/wikipedia-disable-fundraiser-300x153.png"><img src="../images/2013/01/wikipedia-disable-fundraiser-300x153.png" alt="How to disable Wikipedia fundraiser" width="" height="" class="size-medium wp-image-53051" /></a><p class="wp-caption-text">How to disable Wikipedia fundraiser</p></div> <p>You only have to go to:</p> <p>Preferences → Gadgets tab → Browsing → check “Suppress display of the fundraiser banner”</p> <p>Now I’m happy ☺</p> PDF-Printing on Windows 7 //martin-thoma.com/pdf-printing-on-windows-7/ Mon, 31 Dec 2012 17:23:10 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/pdf-printing-on-windows-7 <p>“Printing” files on PDF-printers is useful as you can save everything as a digital PDF file instead of printing it.</p> <p>I’ve just installed <a href="http://www.heise.de/download/typing-test-tq-1128987.html">Typing Test TQ</a> for testing my typing speed and I wanted to save my results. This wasn’t possible, but I could print them. So I thought I could print it to a PDF file and store it this way on my computer. Once again, I didn’t think of Microsoft.</p> <h2>The Linux-Way</h2> <p>How would you solve this problem on a Debian machine? Well, most Debian machines would have a PDF printer pre-installed. So you would simply click on print, choose the PDF printer and be happy.</p> <p>If it is not pre-installed, type:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install cups-pdf</code></pre></div> <p>Now you can use a PDF printer.</p> <p>Done. It works.</p> <h2>The Windows-Way</h2> <p>Windows 7 does not have a PDF printer, but it has a “Microsoft XPS Document Writer”. Lets see what this is:</p> <h3>XPS</h3> <h4>General Information</h4> <p><a href="http://en.wikipedia.org/wiki/Open_XML_Paper_Specification">Open XML Paper Specification</a> is an open specification for a page description language and a fixed-document format originally developed by Microsoft as XML Paper Specification (XPS) that was later standardized by Ecma International as international standard ECMA-388. It is an XML-based specification, based on a new print path and a color-managed vector-based document format that supports device independence and resolution independence. OpenXPS was standardized as an open standard document format on June 16, 2009.</p> <h4>XPS vs. PDF</h4> <ul> <li><a href="http://en.wikipedia.org/wiki/Comparison_of_OpenXPS_and_PDF">Comparison of OpenXPS and PDF</a></li> <li><a href="http://superuser.com/questions/73206/xps-vs-pdf-whats-the-status">XPS vs PDF. What's the status?</a> on superusers</li> </ul> <h4>TL;DR</h4> <p>XPS is an alternative for PDF. It lacks program support compared to PDF.</p> <h3>Getting a PDF-Printer</h3> <p>After a quick search, I found <a href="http://www.cutepdf.com/Products/CutePDF/writer.asp">CutePDF</a>. Seems to work, but I don’t give any malware-freeness-guarantees.</p> <p>Although I don’t know if there is malware, there is definitely some spam content:</p> <div style="width: 528px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-7-browser-toolbar.png"><img src="../images/2012/12/windows-7-browser-toolbar.png" alt="Windows 7: Install another browser toolbar" width="" height="" class="size-full wp-image-52891" /></a><p class="wp-caption-text">Windows 7: Install another browser toolbar</p></div> <p>Why can’t it simply only install a PDF-printer without getting annoyed with toolbars? I never had this problem on Linux…</p> Unreal Tournament 2004 //martin-thoma.com/unreal-tournament-2004/ Mon, 31 Dec 2012 13:49:40 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/unreal-tournament-2004 <p>I am currently at home and I found <a href="http://en.wikipedia.org/wiki/Unreal_Tournament_2004">Unreal Tournament 2004</a> in my old stuff. Of course, I had to play it again ☺</p> <p>Before you start, you might want to get the latest version. You have to find the patches by yourself. According to <a href="http://liandri.beyondunreal.com/Unreal_Tournament_2004#Patches">this page</a>, you get all updates / bonus content with “<a href="http://liandri.beyondunreal.com/Unreal_Tournament_2004#Bonus_Packs">Mega Pack</a>” (201 MB).</p> <p>It’s asthonishing that there is neither a possibility to upgrade the game within the game, nor an official source for patches. I guess providing a patches is an easy way to spread viruses. Do I have any chance to check if it’s a valid patch or a patch with a virus?</p> <h2>Error</h2> <p>I played “COPT - Camper and Sniper” for about half an hour and got this error:</p> <blockquote>UT2004 Build UT2004_Build_[2005-11-23_16.22] OS: Windows NT 6.1 (Build: 7601) CPU: GenuineIntel PentiumPro-class processor @ 2133 MHz with 3764MB RAM Video: Intel(R) HD Graphics (2372) General protection fault! History: UObject::ConditionalDestroy &lt;- UObject::GetFullName &lt;- DispatchDestroy &lt;- DispatchDestroys &lt;- UObject::PurgeGarbage &lt;- UObject::CollectGarbage &lt;- UObject::StaticExec &lt;- UEngine::Exec &lt;- UGameEngine::Exec &lt;- UPlayer::Exec &lt;- UViewport::Exec &lt;- UWindowsViewport::Exec &lt;- APlayerController::execConsoleCommand &lt;- (ExtendedConsole Package.ExtendedConsole @ Function Engine.Console.Tick : 002C) &lt;- UObject::ProcessEvent &lt;- (InteractionMaster Package.InteractionMaster, Function Engine.InteractionMaster.Process_Tick) &lt;- UInteractionMaster::MasterProcessTick &lt;- ULevel::Tick &lt;- (NetMode=0) &lt;- TickLevel &lt;- UGameEngine::Tick &lt;- Level Unbenannt &lt;- UpdateWorld &lt;- MainLoop &lt;- FMallocWindows::Free &lt;- FMallocWindows::Realloc &lt;- 10910191 0 FArray &lt;- FArray::Realloc &lt;- 0*2 &lt;- FMallocWindows::Free</blockquote> <h2>Some Links</h2> <ul> <li><a href="http://www.gamefaqs.com/pc/914986-unreal-tournament-2004/faqs/31756">Team stats</a> by Hammerlock770 (another version is <a href="../images/2012/12/ut2004-team-stats.txt">here</a>, if the linked site gets offline)</li> <li><a href="http://ut2004stats.epicgames.com/index.php">UT2004 Stats</a></li> <li><a href="http://forums.epicgames.com/forums/249-Unreal-Tournament-2003-2004">Official forum</a></li> </ul> My blog in 2012 //martin-thoma.com/my-blog-in-2012/ Sun, 30 Dec 2012 14:00:25 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/my-blog-in-2012 <p>I get a lot of data about my visitors which I would like to share. The following data is from 2012 of my domain martin-thoma.com. It was collected by Piwik. Note that I excluded my visits.</p> <h2>Articles</h2> <p>These articles had the most visitors:</p> <ol> <li><a href="../how-to-draw-a-finite-state-machine/">How to draw a finite-state machine</a></li> <li><a href="../matrix-multiplication-python-java-cpp/">Performance of Matrix multiplication in Python, Java and C++</a></li> <li><a href="../latex-vorlage-fur-ein-lastenheft/">LaTeX-Vorlage f&uuml;r ein Lastenheft</a> (german)</li> <li><a href="../computer-science-jokes/">Computer Science Jokes</a></li> <li><a href="../wie-fuhre-ich-einen-induktionsbeweis/">Wie f&uuml;hre ich einen Induktionsbeweis?</a> (german)</li> </ol> <p>Recently, my article <a href="../frauenquote-am-kit/">Frauenquote am KIT</a> got also very popular.</p> <h2>Visitors</h2> <p>According to awstats:</p> <ul> <li>Different users: 81,028</li> <li>Visits: 119,855</li> <li>Page accesses: 2,379,654</li> <li>Bytes sent: 27.95 GB</li> </ul> <p>According to Piwik:</p> <div style="width: 424px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitor-increase.png"><img src="../images/2012/12/2012-visitor-increase.png" alt="Number of visitors of my blog - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52691" /></a><p class="wp-caption-text">Number of visitors of my blog</p></div> <h3>Where do they come from?</h3> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-continent.png"><img src="../images/2012/12/2012-visitors-continent.png" alt="Continent - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52611" /></a><p class="wp-caption-text">Continent - Piwik Statistics 2012</p></div> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-country.png"><img src="../images/2012/12/2012-visitors-country.png" alt="Country - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52621" /></a><p class="wp-caption-text">Country - Piwik Statistics 2012</p></div> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-region.png"><img src="../images/2012/12/2012-visitors-region.png" alt="Region - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52661" /></a><p class="wp-caption-text">Region - Piwik Statistics 2012</p></div> <h3>Hardware</h3> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-screen-size.png"><img src="../images/2012/12/2012-visitors-screen-size.png" alt="Screen size - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52671" /></a><p class="wp-caption-text">Screen size</p></div> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-desktop-vs-mobile.png"><img src="../images/2012/12/2012-visitors-desktop-vs-mobile.png" alt="Desktop vs. Mobile - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52631" /></a><p class="wp-caption-text">Desktop vs. Mobile</p></div> <h3>Software</h3> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-os.png"><img src="../images/2012/12/2012-visitors-os.png" alt="Operating Systems - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52641" /></a><p class="wp-caption-text">Operating Systems</p></div> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-browser-family.png"><img src="../images/2012/12/2012-browser-family.png" alt="Browser families - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52581" /></a><p class="wp-caption-text">Browser families</p></div> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-browser.png"><img src="../images/2012/12/2012-visitors-browser.png" alt="Browsers - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52601" /></a><p class="wp-caption-text">Browsers</p></div> <div style="width: 467px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-browser-plugins.png"><img src="../images/2012/12/2012-browser-plugins.png" alt="Browser Plugins - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52591" /></a><p class="wp-caption-text">Browser Plugins</p></div> <h3>Provider</h3> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-visitors-provider.png"><img src="../images/2012/12/2012-visitors-provider.png" alt="Providers - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52651" /></a><p class="wp-caption-text">Providers</p></div> <h2>Referrers</h2> <div style="width: 477px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-referrers.png"><img src="../images/2012/12/2012-referrers.png" alt="Referrers - Piwik Statistics 2012" width="" height="" class="size-full wp-image-52701" /></a><p class="wp-caption-text">Referrers</p></div> <p>Obviously, search engines are much more important for my website than other websites. Visitors who find me with Google, use these terms:</p> <ol> <li>"lastenheft vorlage" or "lastenheft beispiel" &rarr; <a href="../latex-vorlage-fur-ein-lastenheft/">LaTeX-Vorlage f&uuml;r ein Lastenheft</a></li> <li>"induktionsbeweis" &rarr; <a href="../wie-fuhre-ich-einen-induktionsbeweis/">Wie f&uuml;hre ich einen Induktionsbeweis?</a></li> <li>"computer science jokes" &rarr; <a href="../computer-science-jokes/">Computer Science Jokes</a></li> <li>"basiswechselmatrix" &rarr; <a href="../wie-bestimme-ich-die-basiswechselmatrix/">Wie bestimme ich die Basiswechselmatrix?</a></li> <li>"chomsky normalform" &rarr; <a href="../konstruktion-der-chomsky-normalform/">Konstruktion der Chomsky-Normalform</a></li> </ol> <h2>Spam</h2> <p>Akistmet got a lot of comment spam on my blog:</p> <div style="width: 545px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-akismet-stats-total.png"><img src="../images/2012/12/2012-akismet-stats-total.png" alt="Akismet total stats for 2012" width="" height="" class="size-full wp-image-52721" /></a><p class="wp-caption-text">Akismet total stats for 2012</p></div> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/12/2012-akismet-stats.png"><img src="../images/2012/12/2012-akismet-stats.png" alt="Akismet spam stats for 2012" width="" height="" class="size-full wp-image-52711" /></a><p class="wp-caption-text">Akismet spam stats for 2012</p></div> How fast are electrons moving? //martin-thoma.com/how-fast-are-electrons-moving/ Fri, 28 Dec 2012 07:04:47 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-fast-are-electrons-moving <p>I’ve recently learned something about electric circuits. The ideal model of circuits does ignore that electrons actually need time to pass the components of the circuit. So we introduced the “dead time model”. So we added a model component for each real component that does only delay the incoming signal. But I’ve wondered if dead time of a cable wasn’t important, too. So I thought the question would be <em>How fast are electrons moving in a cable?</em>, but I just realized that the question is <em>How fast does a signal move in a wire?</em>.</p> <h2>How fast are electrons moving through a wire?</h2> <p>If you have electric current <code>$I$</code> (measured in Ampere), the wire is a cylindric conductore with a cross-sectional area of <code>$A$</code>, <code>$e = -1.6021766 \cdot 10^{-19} C$</code> (coulombs) is the charge of an electron an <code>$Q$</code> is <code>$\frac{\text{mobile electrons}}{\text{volume}}$</code>. <code>$v = \frac {I}{QeA}$</code></p> <p>According to this source, <code>$Q = 8.5 \cdot 10^{22} \frac{1}{cm^3}$</code> for copper. If <code>$I=1 A$</code> and if your wire has a radius of 0.5mm, you get: <code>$v= \frac{1 A}{ 8.5 \cdot 10^{22} \frac{1}{cm^3} \cdot e \cdot ((0.5mm)^2 \cdot pi)} = 9.349 \cdot 10^{-5} \frac{m}{s} = $</code> (see <a href="http://www.wolframalpha.com/input/?i=%281+A%29%2F%288.5+*+10%5E%2822%29%2F%28cm%5E3%29+*+%28charge+of+an+electron%29+*+%28%280.5mm%29%5E2+*+pi%29%29">Wolfram|Alpha</a>).</p> <p>Hmm … seems to be very slow. Is my calculation correct?</p> <h2>How fast are electrical signals moving through a wire?</h2> <p>See <a href="http://physics.stackexchange.com/a/47635/7197">physics.stackexchange.com</a></p> <p><code>$v = \frac{c}{\sqrt{\mu_r \varepsilon_r}}$</code></p> <p>where <code>$\varepsilon_r$</code> is <a href="http://en.wikipedia.org/wiki/Relative_permittivity">relative permittivity</a> and <code>$\mu_r$</code> is <a href="http://en.wikipedia.org/wiki/Permeability_(electromagnetism)#Relative_permeability">relative magnetic susceptibility</a>.</p> <p>For copper: <code>$\mu_r = 0.999994$</code> <code>$\varepsilon_r = 3$</code>, as you can’t measure permeability of metallic conductors (see “Elektromagnetische Felder und Wellen”. Paul Lorrain, Dale R. Corson, François Lorrain, page 75) <code>$v = \frac{c}{\sqrt{0.999994 \cdot 3}} = 0.577352 \cdot c$</code></p> <h2>How fast are electrons moving around an atom?</h2> <p>Well, first of all I have to mention, that electrons seem not to move around a nucleus as this image suggests:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/atom-electron-bohr-300x300.png"><img src="../images/2012/12/atom-electron-bohr-300x300.png" alt="Atom according to Bohrs model" width="" height="" class="size-medium wp-image-52041" /></a><p class="wp-caption-text">Atom according to Bohrs model</p></div> <p>A model with <a href="http://en.wikipedia.org/wiki/Atomic_orbital">atomic orbitals</a> seems to be more accurate. However, you can calulate the speed <code>$v$</code> an electron would have in Bohrs model.</p> <p>The centripedal force is <code>$F_Z = \frac{m \cdot v^2}{r}$</code> This force pushes the electron away from the nucleus.</p> <p>The coulomb-force is <code>$F_C = \frac{e^2}{4 \pi \varepsilon_0 r^2}$</code> where <code>$\varepsilon_0 \approx 8.8541 \cdot 10^{-12} \frac{F}{m}$</code> is <a href="http://en.wikipedia.org/wiki/Permittivity">permittivity</a>.</p> <p>Now you calculate: <code>$\begin{align}F_\mathrm{C} = F_\mathrm{Z} \quad &amp;\Leftrightarrow \quad \frac{e^2}{4 \pi \varepsilon_0 r^2} = \frac{m_{e}v^2}{r}\\ &amp;\Leftrightarrow \quad v^2 = \frac{e^2}{4 \pi \varepsilon_0 r m_e} = \frac{e^2}{4 \pi \varepsilon_0 m_e} \cdot \frac{1}{r} \end{align}$</code></p> <p>Ok, we’re almost there. But how do we get <code>$r$</code>? Well, you have to know this equation: <code>$ m_{e} v r = n \hbar$</code> where <code>$n$</code> is the <a href="http://en.wikipedia.org/wiki/Principal_quantum_number">principal quantum number</a> and <code>$\hbar$</code> is the <a href="http://en.wikipedia.org/wiki/Planck_constant">reduced Planck constant</a>. So you get: <code>$\Leftrightarrow r = \frac{n \hbar}{v m_e}$</code></p> <p>Now insert this in the equation above: <code>$\begin{align} v^2 &amp;= \frac{e^2}{4 \pi \varepsilon_0 m_e} \cdot \frac{1}{\frac{n \hbar}{v m_e}}\\ \Rightarrow v &amp;= \frac{e^2}{4 \pi \varepsilon_0 n \hbar} \end{align}$</code></p> <p>Lets take a hydrogen nucleus (<code>$n=1$</code>): We get <code>$2.19 \cdot 10^6 \frac{m}{s} \approx 7.88 \cdot 10^6 \frac{km}{h}$</code> (see <a href="http://www.wolframalpha.com/input/?i=%28charge+of+electron%29%5E2%2F%284+pi+epsilon_0+h+bar%29">Wolfram|Alpha</a>). This is much less than 1% of the speed of light (which is <code>$1.079 \cdot 10^9 \frac{km}{h}$</code>)</p> <h2>Sources</h2> <p>Very good:</p> <ul> <li><a href="http://physics.stackexchange.com/q/20187/7197">How fast do electrons travel in an atomic orbital?</a></li> <li><a href="http://physics.stackexchange.com/q/6177/7197">How fast do electrons move through a conductor?</a> &rarr; <a href="http://amasci.com/miscon/speed.html">SPEED OF "ELECTRICITY"</a></li> <li><a href="http://physics.stackexchange.com/q/15704/7197">Explanation for speed of an electrical impulse</a></li> </ul> <p>Not so good:</p> <ul> <li><a href="http://en.wikipedia.org/wiki/Drift_velocity">Drift velocity</a></li> <li><a href="http://en.wikipedia.org/wiki/Speed_of_electricity">Speed of electricity</a></li> <li><a href="http://en.wikipedia.org/wiki/Wave_propagation_speed">Wave propagation speed</a></li> </ul> C++ Preprocessor Snippets //martin-thoma.com/c-preprocessor-snippets/ Tue, 25 Dec 2012 19:32:31 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/c-preprocessor-snippets <p>The C++ Preprocessor - which is in fact the same as the C Preprocessor - provides some very basic, but powerful abilities. I haven’t used them quite often, but I have seen some nice examples. So here are some C++ Preprocessor Snippets:</p> <h2>Maximum / Minimum</h2> <p>If you want to find the maximum / minimum of two elements, no matter of which type, you can do something like this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#define MAX(a, b) ((a &lt; b) ? b : a)</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">MAX</span><span class="p">(</span><span class="mi">42</span><span class="p">,</span> <span class="mi">1337</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">MAX</span><span class="p">(</span><span class="mi">1337</span><span class="p">,</span> <span class="mi">42</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">MAX</span><span class="p">(</span><span class="o">-</span><span class="mi">1337</span><span class="p">,</span> <span class="mi">42</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">MAX</span><span class="p">(</span><span class="mf">1337.0</span><span class="p">,</span> <span class="mi">42</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>Absolute Value</h2> <p>You can get the absolute value like this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#define ABS(a) (a &lt; 0 ? -(a) : a)</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">a</span> <span class="o">=</span> <span class="mi">42</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="o">-</span><span class="mi">43</span><span class="p">,</span> <span class="n">c</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">d</span> <span class="o">=</span> <span class="o">-</span><span class="mi">1337</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">ABS</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">ABS</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">ABS</span><span class="p">(</span><span class="n">c</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">ABS</span><span class="p">(</span><span class="n">d</span><span class="p">)</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>By the way, brackets around <code>a</code> are important, because without them you could get:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">a=1,b=3 ABS(a-b) = ABS(1-3) = (1-3 &lt; 0 ? -1-3 : 1-3) = -2 &lt; 0 ? -4 : -2 = -4</code></pre></div> <h2>Swap variable content</h2> <p>This is an example for a multiline replacement.</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#define SWAP(a, b) { int tmp; \</span> <span class="cp"> tmp = b; \</span> <span class="cp"> b = a; \</span> <span class="cp"> a = tmp; \</span> <span class="cp"> }</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">a</span> <span class="o">=</span> <span class="mi">42</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="mi">1337</span><span class="p">;</span> <span class="n">swap</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">);</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">a</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">b</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/C_preprocessor">C preprocessor</a></li> <li>Tips and tricks using the preprocessor: <a href="http://www.iar.com/Global/Resources/Developers_Toolbox/C_Cplusplus_Programming/Tips%20and%20tricks%20using%20the%20preprocessor%20(part%20one).pdf">Part one</a> - <a href="http://www.iar.com/Global/Resources/Developers_Toolbox/C_Cplusplus_Programming/Tips%20and%20tricks%20using%20the%20preprocessor%20(part%20two).pdf">part two</a><br /> A very good article about the meaning of #import, #error, #pragma. It is written very well and has some examples.</li> <li>Obfuscated C: <a href="http://www.cise.ufl.edu/~manuel/obfuscate/pi.c">Calculate PI</a></li> </ul> <p>Do you know more preprocessor snippets that are used very often or which are interesting?</p> Wie wendet man den Transformationssatz an? //martin-thoma.com/wie-wendet-man-den-transformationssatz-an/ Sat, 22 Dec 2012 22:43:11 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-wendet-man-den-transformationssatz-an <div class="info">Folgender Artikel basiert auf meinem Mitschrieb der Analysis III &Uuml;bung bei Herrn Bolleyer.</div> <p>Sei <code>$A \in \mathfrak{B}_d$</code> mit <code>$A^0 \neq \emptyset$</code> und <code>$\lambda_d (A \setminus A^0) = 0$</code> sowie <code>$\phi \in C^1(U, \mathbb{R}^d)$</code> mit <code>$U \subseteq \mathbb{R}^d$</code> offen und <code>$A \subseteq U$</code>. Weiter sei <code>$\phi$</code> auf <code>$A^0$</code> injektiv und <code>$\det(\phi'(x)) \neq 0$</code> für <code>$x \in A^0$</code>. Sei <code>$f \in \mathfrak{L}^1(\phi(A))$</code> oder <code>$f \geq 0$</code> auf <code>$A$</code> so gilt <code>$\int_{\phi(A)} f(x) dy = \int_A f(\phi(x)) | \det(\phi'(x)) | dx$</code></p> <p>In Anwendungen: <code>$Y \in \mathfrak{B}_d$</code> und <code>$f: Y \rightarrow \overline{\mathbb{R}}$</code> messbar.</p> <p><strong>Aufgabe</strong>: Berechne <code>$\int_Y f(x) dy$</code> falls es existiert. <strong>Vorgehensweise:</strong></p> <ol type="i" style="list-style-type:lower-roman;"> <li>Zeige `$f$` integrierbar oder `$f \geq 0$` auf `$Y$`</li> <li>Finde `$A \in \mathfrak{B}_d$` und `$\phi: A \rightarrow \mathbb{R}^d$` mit `$\phi(A) = Y$` und den obigen Eigenschaften<br /> `$\phi$` sollte so gew&auml;hlt sein, dass die sp&auml;teren Rechenwege relativ einfach werden.</li> <li>Berechne `$\int_{Y} f(y) dy = \int_{\phi(A)} f(y) dy = \int_{A} f(\phi(x)) |\det (\phi'(x)) | dx$`</li> </ol> <h2>Beispiele</h2> <p>Sei <code>$Y := \{(x,y) \in \mathbb{R}^2 | 1 \leq \| (2,2) - (x,y)\| \leq 2\}$</code>. Setze <code>$\phi : \mathbb{R}^2 \rightarrow \mathbb{R}^2$</code> mit <code>$\phi(r, \varphi) := \begin{pmatrix}2\\2\end{pmatrix} + r \cdot \begin{pmatrix}\cos(\varphi)\\ \sin(\varphi) \end{pmatrix}$</code></p> <p><code>$\phi \in C^1(\mathbb{R}^2, \mathbb{R}^2)$</code> und für <code>$r \in \mathbb{R}$</code> gilt <code>$\det \phi'(r, \varphi) = \det \left ( \begin{array}{cc} \cos(\varphi) &amp; - r \sin(\varphi)\\ \sin(\varphi) &amp; r \cos (\varphi) \end{array} \right ) = r$</code></p> <p>Für <code>$r \neq 0$</code> gilt also <code>$\det \phi'(r, \varphi) \neq 0$</code> für jedes <code>$\varphi \in \mathbb{R}$</code>. <code>$\phi$</code> ist nicht injektiv auf <code>$\mathbb{R}^2$</code>. Setze <code>$A := [1,2] \times [0, 2\pi]$</code>.</p> <p>Dann ist <code>$A^0 = (1,2) \times (0,2 \pi)$</code> und<code>$ \phi$</code> auf <code>$A^0$</code> injektiv. Außerdem ist <code>$\det \phi'(x) \neq 0$</code> für <code>$x \in A^0$</code>.</p> <p>Für <code>$f:Y \rightarrow \mathbb{R}$</code> mit <code>$f(Y_1, Y_2) := Y_1 - Y_2$</code> gilt <code>$f \in \mathfrak{L}^1(Y)$</code> (<code>$Y$</code> kompakt, <code>$f$</code> stetig)</p> <p>Außerdem: <code>$\begin{align} \int_Y f(y) dy &amp;= \int_\phi(A) f(y) dy \\ &amp;\stackrel{Tr}{=} \int_A f(\phi(r, \varphi)) |\det \phi'(r, \varphi)| d(r, \varphi) \\ &amp;= \int_A r(2 + r \cos(y) - 2 - r \sin(\varphi)) d(r, \varphi) \\ &amp;= \int_1^2 (\int_0^{2\pi} r^2 (\cos \varphi - \sin \varphi d \varphi) dr \\ &amp;= \underbrace{(\int_1^2 r^2 dr)}_{&lt; \infty} \underbrace{(\int_0^{2\pi} \cos \varphi - \sin \varphi d \varphi)}_{= 0}\\ &amp;= 0 \end{align}$</code></p> Blender Open Movies //martin-thoma.com/blender-open-movies/ Sat, 22 Dec 2012 17:00:46 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/blender-open-movies <h2>Big Buck Bunny</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/YE7VzlLtp-4" frameborder="0" allowfullscreen=""></iframe> <h2>Elephants Dream</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/TLkA0RELQ1g" frameborder="0" allowfullscreen=""></iframe> <h2>Sintel</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/eRsGyueVLvQ" frameborder="0" allowfullscreen=""></iframe> <h2>More information</h2> <ul> <li><a href="http://www.sintel.org/">www.sintel.org</a></li> <li>Soundtrack: <a href="http://www.youtube.com/watch?feature=player_embedded&amp;v=AeFwEnyMl8A">I Move On</a></li> </ul> Why are Microsoft products so User unfriendly? //martin-thoma.com/why-are-microsoft-products-so-user-unfriendly/ Fri, 21 Dec 2012 17:00:31 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/why-are-microsoft-products-so-user-unfriendly <p>Another rage-post …</p> <h2>Loading times</h2> <p>Did you ever work with eclipse? Then you might know the feeling, that it takes an eternity until Eclipse has started. I’ve just stopped it.</p> <p>Eclipse takes 30 seconds to start:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/eclipse-juno-loading-300x200.png"><img src="../images/2012/12/eclipse-juno-loading-300x200.png" alt="Eclipse Juno loading screen" width="" height="" class="size-medium wp-image-51161" /></a><p class="wp-caption-text">Eclipse Juno loading screen</p></div> <p>Visual Studio 2012 takes 1 minute and 15 seconds to start:</p> <div style="width: 239px" class="wp-caption aligncenter"><a href="../images/2012/12/visual-studio-2012-loading-229x300.png"><img src="../images/2012/12/visual-studio-2012-loading-229x300.png" alt="Visual Studio Ultimate - Loading screen" width="" height="" class="size-medium wp-image-51171" /></a><p class="wp-caption-text">Visual Studio Ultimate - Loading screen</p></div> <p>But that’s not the worst. It’s okay if it takes long to start, if it’s later a swift. But it’s not. I get those loading screens from time to time without having done anything:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/visual-studio-2012-loading-times-300x202.png"><img src="../images/2012/12/visual-studio-2012-loading-times-300x202.png" alt="Visual Studio 2012 - loading something without any action from my side" width="" height="" class="size-medium wp-image-51181" /></a><p class="wp-caption-text">Visual Studio 2012 - loading something without any action from my side</p></div> <p>Why is it loading something from time to time without interaction? What does Visual Studio load?</p> <h2>Control</h2> <p>The next big problem I have with Microsoft products is the lack of control. I would like to know what are the effects of a command I use before I use it - no matter if it is a command line command or a GUI or key-press-combination command. As it is very difficult to make GUI commands unambiguous, I really like the command line for some tasks. Why doesn’t Windows offer a default command line that is usable? I mean, yes, you have the PowerShell … but why isn’t it the default shell? Why does the user have to know that there are other (better?) shells? Is there any reason not to use the PowerShell in Windows 7? And even the PowerShell misses some really basic tools. I mean, did you try the path autocompletion (with tab) on bash (the Linux shell)? It completes the path / command, if there is only one possibility. If there are more possibilities, the user gets displayed all options (if there are too many, he will get asked before all are displayed). The Windows-shells go through each possibility.</p> <p>Here are some screenshots of the shells displaying the content of the current folder:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/CWindowssystem32cmd-300x204.png"><img src="../images/2012/12/CWindowssystem32cmd-300x204.png" alt="Windows32 cmd" width="" height="" class="size-medium wp-image-51251" /></a><p class="wp-caption-text">Windows32 cmd</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/WindowsPowerShellv1.0-300x231.png"><img src="../images/2012/12/WindowsPowerShellv1.0-300x231.png" alt="Windows PowerShell v1.0" width="" height="" class="size-medium wp-image-51261" /></a><p class="wp-caption-text">Windows PowerShell v1.0</p></div> <p>Now compare this to Linux:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/gnome-shell-300x117.png"><img src="../images/2012/12/gnome-shell-300x117.png" alt="Gnome shell (bash)" width="" height="" class="size-medium wp-image-51271" /></a><p class="wp-caption-text">Gnome shell (bash)</p></div> <p>Where do you find easier what you need? And why do they have a black background with white font color? Try to work with this for some hours and than compare it to a shell with black font size and white background…</p> <h3>Missing (command line) tools</h3> <p>I like using git / svn from command line. But the default way to use SVN (and eventually GIT) seems to be by GUI. Why results in a crappy, overblown right click menu:</p> <div style="width: 297px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-right-click-287x300.png"><img src="../images/2012/12/windows-right-click-287x300.png" alt="Windows right click menu" width="" height="" class="size-medium wp-image-51291" /></a><p class="wp-caption-text">Windows right click menu</p></div> <p>Now compare this to Linux 10.04 with GNOME:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/gnome-2-right-click-300x292.png"><img src="../images/2012/12/gnome-2-right-click-300x292.png" alt="Right click menu on GNOME 2" width="" height="" class="size-medium wp-image-51311" /></a><p class="wp-caption-text">Right click menu on GNOME 2</p></div> <p>And I should also mention that I didn’t clean up my Linux system for over one year. I use it every day, install new software, remove software, forget to remove software. I have git and svn on my Linux machine as well as Apache, Python, some games, …</p> <p>The Windows 7 machine is a fresh install. It has better hardware and I only use it for work (so it basically only has TurtoiseSVN, Visual Studio and IIS). I guess this would be even worse if I used it every day.</p> <h3>Updates</h3> <p>Windows makes its updates at very bad times. Sometimes it just makes an update and you have to wait for quarter of an hour to finish it, before you can shut down. Why? Can’t you just ask the user before you make an update? A friend of mine had a tutorial after which she wanted to go to a Christmas party. Guess what happened: Before she could shut down the computer, Windows decided to make automatically an update. Took about 15 - 20 minutes. No Christmas parties for Windows users.</p> <div style="width: 436px" class="wp-caption aligncenter"><a href="../images/2012/12/shutdown-windows.png"><img src="../images/2012/12/shutdown-windows.png" alt="Automatic shutdown of Windows" width="" height="" class="size-full wp-image-54251" /></a><p class="wp-caption-text">Automatic shutdown of Windows</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-7-automatic-update-installation-300x225.jpg"><img src="../images/2012/12/windows-7-automatic-update-installation-300x225.jpg" alt="Windows 7: Automatic update installation" width="" height="" class="size-medium wp-image-54261" /></a><p class="wp-caption-text">Windows 7: Automatic update installation</p></div> <p>Windows really shut down my computer automatically and blocked it for about 15 minutes. What if I had to hold a presentation? What if I downloaded something?</p> <h2>Nice features, crappy realization</h2> <p>Windows has a very nice feature: You an search at the “start”. But why doesn’t it work for every program? I’ve searched for “winver.exe”, a program shipped per default from Microsoft. Why can’t you find this in start?</p> <div style="width: 250px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-start-search-240x300.png"><img src="../images/2012/12/windows-start-search-240x300.png" alt="Windows Start search" width="" height="" class="size-medium wp-image-51281" /></a><p class="wp-caption-text">Windows Start search</p></div> <p>If I have to type the whole name, this feature is essentially useless…</p> <p><a href="http://en.wikipedia.org/wiki/Outlook_Web_App">Microsoft OWA</a> is an online email service. A friend showed me this usability desaster:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/microsoft-owa-300x157.png"><img src="../images/2012/12/microsoft-owa-300x157.png" alt="Microsoft OWA" width="" height="" class="size-medium wp-image-54791" /></a><p class="wp-caption-text">Microsoft OWA</p></div> <h2>No structure for programs</h2> <p>Where do programs get installed?</p> <ul> <li>C:\</li> <li>C:\Program Files</li> <li>C:\Program Files (x86)</li> </ul> <p>If you have a German system, the explorer will show a German path although the underlying path is English. What the hell? And <a href="../microsoft-product-flavor-hell/" title="Microsoft product flavor hell">switching languages isn’t easy on Microsofts Systems</a>.</p> <h2>Drivers</h2> <h3>Installation CD</h3> <p>Although many drivers exist for Windows, you have to install them almost always by CD.</p> <h3>Mouse drivers</h3> <p>You have to INSTALL mouse drivers! WTF! I expect an USB mouse to work immediately and not to get something like that:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/usb-mouse-windows-7-300x101.png"><img src="../images/2012/12/usb-mouse-windows-7-300x101.png" alt="Installing USB mouse in Windows 7" width="" height="" class="size-medium wp-image-52321" /></a><p class="wp-caption-text">Installing USB mouse in Windows 7</p></div> <h2>Windows Explorer</h2> <h3>No tabs</h3> <p>Clover tries to fix that, but I don’t want to install a third party tool for such a basic tool.</p> <h3>Structure</h3> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-7-explorer-300x220.png"><img src="../images/2012/12/windows-7-explorer-300x220.png" alt="Windows 7 Explorer" width="" height="" class="size-medium wp-image-52481" /></a><p class="wp-caption-text">Windows 7 Explorer</p></div> <h2>Shell</h2> <p>There is so much wrong with the Windows Shells:</p> <ul> <li>You can't maximize it (see <a href="http://superuser.com/a/80098/64857">explantation</a>)</li> <li>Crappy autocomplete: In Linux, if you have multiple ways to autocomplete, you get a list of the options. Windows 7 only pics the first.</li> <li>PowerShell: Its soooo slow! I don't want to wait for my shell to start!</li> </ul> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/full-screen-terminal-300x169.png"><img src="../images/2012/12/full-screen-terminal-300x169.png" alt="Windows Terminal in 'Full Screen'" width="" height="" class="size-medium wp-image-54771" /></a><p class="wp-caption-text">Windows Terminal in 'Full Screen'</p></div> <h2>A wrap-up for Windows 8</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/WTYet-qf1jo" frameborder="0" allowfullscreen=""></iframe> <h2>Microsoft Bob</h2> <p>Have you ever heard of <a href="http://en.wikipedia.org/wiki/Microsoft_Bob">Microsoft Bob</a>? I guess we should not complain about Windows 8 desktop, if you have seen this desktop environment interface…</p> <iframe width="512" height="384" src="http://www.youtube.com/embed/ZegWedG-jk4" frameborder="0" allowfullscreen=""></iframe> How can I sketch an application? //martin-thoma.com/how-can-i-sketch-an-application/ Thu, 20 Dec 2012 01:54:57 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-can-i-sketch-an-application <p>I’ve recently participated in a medium size software project. This project is rather fixed for a web project, so we don’t suffer from rapid changes (“rapid” in terms of other web applications), but nether the less they change. The task seemed to be clear at the beginning, but bit for bit my team of developers discovered details that were not so clear. In this project I have learned that a GUI / prototype driven development can be of great benefit. I assumed this beforehand, but I didn’t expect how much it helped.</p> <p>So, I had the idea to create a good GUI to have something to talk about. How do you create a GUI for a web project?</p> <h2>HTML</h2> <ul> <li>is quite simple</li> <li>I know it very well</li> <li>everything I write is obviously possible to realize</li> </ul> <p>but</p> <ul> <li>the result looks too much like the resulting product. The customer might think that we already have some functional prototype <li>it is also unsatisfying to print HTML pages or screenshots of rendered browser views</li> <li>although HTML is easy, arranging items on a screen might take a while</li> <h2>GIMP</h2> GIMP was the next option I tried, but its disadvantage is too severe to think seriously about using it for rapid GUI prototyping: It takes ages! A friend of mine helped me out of my misery. He told me of a product called "<a href="http://www.balsamiq.com/">Balsamiq</a>". <h2>Balsamiq</h2> Balsamiq is easy to use, has a lot of very intuitive features and is able to generate a linked PDF. This means, you can add links to some parts of the interface and simulate interactivity. The user should have opened the slides in full screen, so that on slide fills the screen. Then you might even think it was an web application. Here is <a href="../images/2012/12/Scientific-publishing.pdf">an example PDF created with Balsamiq</a> <h3>What's great about Balsamiq</h3> Balsamiq was carefully designed, is available (and working!) on Windows 7 and Ubuntu 10.04 and via browser. The learning curve is very well. I keep finding new features as I need them. So I first intuitively found the most important ones and recognized advanced ones later. Here are two screenshots of the GUI of the Balsamiq web service: <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/balsamiq-tabs-bar-300x137.png"><img src="../images/2012/12/balsamiq-tabs-bar-300x137.png" alt="Balsamiq GUI overview" width="" height="" class="size-medium wp-image-51021" /></a><p class="wp-caption-text">Balsamiq GUI overview</p></div> Do you see the arrow-symbol? This looks very cool in drafts. Why doesn't GIMP provide anything similar? <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/balsamiq-edit-300x138.png"><img src="../images/2012/12/balsamiq-edit-300x138.png" alt="Edit an element with Balsamiq" width="" height="" class="size-medium wp-image-51031" /></a><p class="wp-caption-text">Edit an element with Balsamiq</p></div> <h3>What I've missed</h3> No application is perfect, so I also found some specials that Balsamiq didn't offer: <ul> <li>Form elements in tables</li> <li>Adjusting table column width</li> </ul> I've found workarounds for both problems, but I guess there could be a better way to solve it. Nevertheless, Balsamiq is a great application that might help a lot to develop great software! </li></ul> When advertising becomes spam //martin-thoma.com/when-advertising-becomes-spam/ Wed, 19 Dec 2012 12:24:20 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/when-advertising-becomes-spam <p>The Web is great. You can easily find and publish information. It is great for trading as you can search through millions of articles and hundreds of vendors to find the product that fits best to your needs and is as cheap as possible. But recently I get a lot of spam from companies I like (<a href="http://en.wikipedia.org/wiki/Amazon.com">Amazon</a>, <a href="http://en.wikipedia.org/wiki/PayPal">PayPal</a> and <a href="http://en.wikipedia.org/wiki/Thalia_(bookstore_chain)">Thalia</a>). I like to get some e-mails from those companies. But how can they provide relevent content instead of spam? When is it good advertising and when does advertising become spam?</p> <h2 id="intervall-of-e-mails">Intervall of E-mails</h2> <p>As a rule of thumb, I would say more e-mails without user-interaction than once a month is spam. So it is perfectly fine if I buy ten products in one week to get ten sales confirmation e-mails. But is not okay to get more than once a month information about the cheapest products, the latest cupons or the latest electronics that I could buy as a present for christmas. Of course, if the user has actively changed the interval of e-mails to once a week or even every day, it is okay to sent him e-mails every day. But this should be opt-in. So the user has to get active to get those e-mails.</p> <h2 id="easy-unsubscribe">Easy unsubscribe</h2> <p>In every e-mail should be a link to unsubscribe from this type of mail. The user should not have to login first, before he can unsubscribe. So the link has to be randomly generated for every user.</p> <h2 id="unambiguous-sender-address">Unambiguous sender address</h2> <p>Thalia uses the address <code>info@produktnews.thalia.de</code> for sending product news. This is great, because I can create a filter that automatically deletes these e-mails. So although the unsubscribe-link doesn’t work, I can get rid of this kind of spam without missing my order confirmations that get sent from <code>info@thalia.de</code> (that should be something like <code>confirmation@thalia.de</code>)</p> <p>Although Thalia has one address that is clearly only for product information, they didn’t solve this problem. They also use <code>thalia@produktnews.thalia.de</code>, what makes it much more difficult for me to filter spam. But it’s better than PayPal. They seem to use <code>paypal@e.paypal.de</code> which could have any content.</p> <h2 id="more-ideas">More ideas?</h2> <p>Does anybody have more ideas how companies could make online advertising, but avoid to spam people?</p> Microsoft product flavor hell //martin-thoma.com/microsoft-product-flavor-hell/ Mon, 17 Dec 2012 13:05:32 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/microsoft-product-flavor-hell <p>As a KIT student I may download pretty much of Microsofts software from a MSDNAA-shop for free. So I’ve downloaded Windows 7 and Visual Studio. I need them for work, so I thought it would be as simple as choosing to download it. But I didn’t think of Microsofts will to make business at the expense of user experience.</p> <h2>Changing the language</h2> <p><strong>The Linux way</strong> If you want to change the language on a Linux (GNOME) system, you have to go to System → Administration → Language support</p> <p>You can choose from 140 languages for free, without any problems. However, most of them are only partially translated, but 28 are fully translated (<a href="http://askubuntu.com/a/229831/10425">source</a>). 10 minutes to search through the menus, 1 minute to change the language.</p> <p><strong>Now the Windows way:</strong> I don’t know where I can change the language in Windows 7, so lets search in the settings.</p> <p>[10 minutes pass]</p> <p>Well, lets google for the right way to achieve a simple language change:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/12/google-search-language-change.png"><img src="../images/2012/12/google-search-language-change.png" alt="Google search for language change in Windows" width="" height="" class="size-full wp-image-50661" /></a><p class="wp-caption-text">Google search for language change in Windows. About 5 minutes.</p></div> <p>So, it seems as if I needed Windows 7 Ultimate or Windows 7 Enterprise edition. Which version do I have? Let’s search … hm, seeems as there are some versions:</p> <div style="width: 520px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-7-editions.jpg"><img src="../images/2012/12/windows-7-editions.jpg" alt="Windows 7 editions" width="" height="" class="size-full wp-image-50681" /></a><p class="wp-caption-text">Windows 7 editions</p></div> <p>And also <a href="../images/2012/12/windows-7-enterprise.jpg"><img src="../images/2012/12/windows-7-enterprise-300x295.jpg" alt="" title="Windows 7 enterprise edition" width="300" height="295" class="aligncenter size-medium wp-image-50691" /></a> and Windows 7 Starter, Windows 7 Home Basic. Did I already mention the family pack? It’s so complicated … there is even a Wikipedia page about <a href="http://en.wikipedia.org/wiki/Windows_7_editions">Windows 7 editions</a>!</p> <p>Find out which version I have (another 15 minutes of searching how to do so):</p> <div style="width: 442px" class="wp-caption aligncenter"><a href="../images/2012/12/winver-search.png"><img src="../images/2012/12/winver-search.png" alt="winver search" width="" height="" class="size-full wp-image-50641" /></a><p class="wp-caption-text">winver search</p></div> <p>And finally:</p> <div style="width: 484px" class="wp-caption aligncenter"><a href="../images/2012/12/winver.png"><img src="../images/2012/12/winver.png" alt="winver" width="" height="" class="size-full wp-image-50651" /></a><p class="wp-caption-text">winver</p></div> <p>Aaaaargh! I don’t have the right edition to be able to change my language to English. I have to reinstall the whole system to get it in English!</p> <p>Well, but as there are so many different editions, there have to be some differences. Lets see if I can find them. [5 minutes later] Oh, Microsoft offers some nice-looking information at <a href="http://windows.microsoft.com/en-US/windows7/products/compare">windows.microsoft.com</a>:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/windows-7-editions-differences-300x152.png"><img src="../images/2012/12/windows-7-editions-differences-300x152.png" alt="Windows 7 editions differences" width="" height="" class="size-medium wp-image-50731" /></a><p class="wp-caption-text">Windows 7 editions differences</p></div> <p>What the #`$@&amp;%*!? Why do they write down similarities? I don’t want to know what’s the same, I want to know the difference! And even the similarities are meaningless. For example</p> <blockquote>Start programs faster and more easily, and quickly find the documents you use most often.</blockquote> <p>If you use comparisons as “faster” or “more easily” you have to say what you compare. Faster than Vista? Faster than DOS? Faster than Linux? All of those lines are meaningless marketing slang that does not offer any useful peace of information and only wastes time.</p> <p>Result: I have wasted about one hour later, I know that I can’t get my system in English without reinstalling it. I have to waste another hour to download it and even one more hour to reinstall it. Linux vs. Windows: 11 minutes of work, nothing to pay vs. 3 hours of work (I got it for free, as I am a student. Otherwise, I might have had to pay about $`150).</p> <h2>Visual Studio</h2> <p>The team I am working with created a diagram on one developers machine. After he had to go, we wanted to continue on another developers machine. So we saved the version and opened it on the other machine. So far so good. After a while we noticed, that we were not able to edit the content of the diagram! The first developer had Visual Studio 2012 Ultimate, the second one “only” Visual Studio 2012 Professional. The difference is obvious, isn’t it? NO, IT IS NOT!</p> <p>Finally, a little story. Some weeks ago, a prof had some problems showing his slides that were made with Microsoft PowerPoint. The bulled points were showing, but not the text. A friend of mine said: “The source of this problem is obvious. He certainly does not have PowerPoint Ultimate” ☺</p> <h2>TL;DR</h2> <p>Microsoft creates a lot of different editions for their software. “Ultimate” seems to be always the best. Microsoft makes things too complicated, without any reason to do so. This video shows what I mean:</p> <iframe width="512" height="384" src="http://www.youtube.com/embed/G9HfdSp2E2A" frameborder="0" allowfullscreen=""></iframe> <p>I don’t understand why a company with that much money, great developers and a lot of user feedback is not able to produce satisfactory, working software.</p> Creating Gantt Charts //martin-thoma.com/creating-gantt-charts/ Thu, 13 Dec 2012 00:02:19 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/creating-gantt-charts <p>I am currently involved in a software project and I should create a Gantt chart. So I’ve searched for tools that allow me to do so, but it was astonishingly difficult to find good tools. I’m not completely content with any of them, but I would like to share my experiences.</p> <h2>Gantter</h2> <h3>Overview</h3> <p><a href="https://app.gantter.com">Gantter</a> is a free online tool that allows you to create Gantt charts.</p> <p>It looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/gantter-overview-300x138.png"><img src="../images/2012/12/gantter-overview-300x138.png" alt="Overview of Gantter" width="" height="" class="size-medium wp-image-50231" /></a><p class="wp-caption-text">Overview of Gantter</p></div> <p>It is easy to use and has a good interface. I can simply define depencies:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/gantter-predecessor-depenency-300x138.png"><img src="../images/2012/12/gantter-predecessor-depenency-300x138.png" alt="Gantter Predecessor depency" width="" height="" class="size-medium wp-image-51101" /></a><p class="wp-caption-text">Gantter Predecessor depency</p></div> <h3>Export</h3> <p>Gantter offers some export options: HTML, <a href="../pdf/UpToDatE-Implementierung.pdf">PDF</a>, <a href="../images/2012/12/UpToDatE-Implementierung.png">PNG</a>, MS-Project (.xml). All export options I’ve tried are unconvincing. I couldn’t save the HTML export, the PDF export was splitted over several pages and the PNG … well, it’s a PNG. As I am currently on a Linux machine, I can’t try the MS-Project export.</p> <h3>Google Drive</h3> <p>Gantter also has a Google Drive integration, but it requests these permissions:</p> <div style="width: 480px" class="wp-caption aligncenter"><a href="../images/2012/12/gantter-google-drive-files.png"><img src="../images/2012/12/gantter-google-drive-files.png" alt="Google Drive permissions requested by Gantter" width="" height="" class="size-full wp-image-50241" /></a><p class="wp-caption-text">Google Drive permissions requested by Gantter</p></div> <p>I have contacted them today (11.12.2012) and asked why they want these permissions. I’ll update this post as soon as I get an answer.</p> <p>My recommendation: Don’t give them those rights! You can create an account without a Google Drive permission.</p> <h2>GanttProject</h2> <p><a href="http://www.ganttproject.biz/">GanttProject</a> is a Java Gantt chart program (as you might have noticed because of the SWING design):</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/GanttProject-300x201.png"><img src="../images/2012/12/GanttProject-300x201.png" alt="GanttProject - Overview" width="" height="" class="size-medium wp-image-50361" /></a><p class="wp-caption-text">GanttProject - Overview</p></div> <p>It’s quite good, but sometimes I got the feeling that it doesn’t instantly response. It’s perhaps imagination as I always think that of Java projects.</p> <p>The HTML-export is not so good. It basically converts the chart to an image and embeds this into a HTML page. This is not what I thought of! This way, you can’t search or copy the tasks. You also can’t see more information about the task.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/GanttProject-export-300x80.png"><img src="../images/2012/12/GanttProject-export-300x80.png" alt="GanttProject export function" width="" height="" class="size-medium wp-image-50371" /></a><p class="wp-caption-text">GanttProject export function</p></div> <h2>GNOME Planner</h2> <p><a href="https://live.gnome.org/Planner">Planner</a> is part of GNOME.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/Planner-300x157.png"><img src="../images/2012/12/Planner-300x157.png" alt="Planner - Overview" width="" height="" class="size-medium wp-image-50291" /></a><p class="wp-caption-text">Planner - Overview</p></div> <p>This is how you create a new task:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/Planner-new-task-300x275.png"><img src="../images/2012/12/Planner-new-task-300x275.png" alt="Planner: Create a new task" width="" height="" class="size-medium wp-image-50381" /></a><p class="wp-caption-text">Planner: Create a new task</p></div> <p>It is very annoying that you always have to click on “Change”, then on “As soon as possible” change it to “fixed date” and then you can click on a date. Why don’t you allow the user to click on a date and when he does, change it automatically to “fixed date”?</p> <p>The HTML-export is good, but I would also like to click on a tasks’ bar and get the associated task highlighted (and perhaps some additional information).</p> <h2>Trac jsGantt plugin</h2> <p>You can let Trac automatically create a Gantt chart with <a href="http://trac-hacks.org/wiki/TracJsGanttPlugin">Trac jsGantt plugin</a>. According to this link, it should look like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/jsGanttSample-300x150.png"><img src="../images/2012/12/jsGanttSample-300x150.png" alt="jsGanttSample" width="" height="" class="size-medium wp-image-50511" /></a><p class="wp-caption-text">jsGanttSample</p></div> <p>I knew that I had to install the <a href="http://trac-hacks.org/wiki/MasterTicketsPlugin">MasterTicketsPlugin</a> to make it possible to add ticket dependencies. With that, it looked like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/jsGantt-without-plugins-300x205.png"><img src="../images/2012/12/jsGantt-without-plugins-300x205.png" alt="jsGantt only with MasterTicketsPlugin" width="" height="" class="size-medium wp-image-50521" /></a><p class="wp-caption-text">jsGantt only with MasterTicketsPlugin</p></div> <p>Not quite what I’ve expected. So I guess I will also need <a href="http://trac-hacks.org/wiki/SubticketsPlugin">SubticketsPlugin</a> and <a href="http://trac-hacks.org/wiki/TimingAndEstimationPlugin">TimingAndEstimationPlugin</a>.</p> <p>Update: These Trac-Plugins are crap. The Gantt-Chart that was created looks ugly and doesn’t look like I’ve expected.</p> <h2>LaTeX</h2> <h3>pgfgantt</h3> <p>This piece of LaTeX:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{article} \usepackage[pdftex,active,tightpage]{preview} \setlength\PreviewBorder{2mm} \usepackage{pgfgantt} \begin{document} \begin{preview} \begin{ganttchart}{12} \gantttitle{2012}{12} \\ \gantttitlelist{1,...,12}{1} \\ \ganttgroup{Group 1}{1}{7} \\ \ganttbar{Task 1}{1}{2} \\ \ganttlinkedbar{Task 2}{3}{7} \ganttnewline \ganttmilestone{Milestone}{7} \ganttnewline \ganttbar{Final Task}{8}{12} \ganttlink{elem2}{elem3} \ganttlink{elem3}{elem4} \end{ganttchart} \end{preview} \end{document} </pre></div> </div> </div> <p>generates this Gantt chart:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/12/gantt-pgf.png"><img src="../images/2012/12/gantt-pgf.png" alt="LaTeX: pgfgantt for creating Gantt charts" width="" height="" class="size-full wp-image-50541" /></a><p class="wp-caption-text">LaTeX: pgfgantt for creating Gantt charts</p></div> <p>Source is <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/gantt-pgf">here</a>.</p> <h3>Another LaTeX Gantt chart solution</h3> <p>This source: ```latex \documentclass{article} \usepackage[pdftex,active,tightpage]{preview} \setlength\PreviewBorder{2mm} \usepackage{gantt}</p> <p>\begin{document} \begin{preview} \begin{gantt}{10}{12} \begin{ganttitle} \numtitle{1}{1}{12}{1} \end{ganttitle} \ganttbar{a task}{0}{2} \ganttbarcon{a consecutive task}{2}{4} \ganttbarcon{another consecutive task}{8}{2} \ganttmilestone[color=cyan]{Milestone with color!}{4} \ganttbar{another task}{2}{2} \ganttbar[color=cyan]{another coloured task}{4}{4} \ganttbar{another task}{4}{2} \ganttcon{4}{5}{4}{7} \ganttmilestonecon{A connected Milestone}{7} \ganttbarcon{another consecutive task}{8}{2} \end{gantt} \end{preview} \end{document} ```</p> <p>creates</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/12/gantt.png"><img src="../images/2012/12/gantt.png" alt="Another Gantt solution" width="" height="" class="size-full wp-image-50551" /></a><p class="wp-caption-text">Another Gantt solution</p></div> <p>Full source is <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents/gantt">here</a>.</p> <p>Although the result looks very nice, I don’t think LaTeX is an optimal solution for Gantt charts of software projects. Yes, you get a great result. But it takes a lot of time and after a week or so this particular chart is definitely outdated. You can’t add more information directly as you could do it with HTML tooltips. I don’t know if you can produce a linked PDF, but I guess this would be quite a lot of manual work.</p> <h2>More tools</h2> <p><a href="http://www.projectlibre.org/">ProjectLibre</a> was recommended to me, but it is not in the Ubuntu repository ☹</p> <h2>Conclusion</h2> <p>LaTeX rulez. If you want nice looking results, you should definitely use LaTeX. Although I think combining an automatically generated Gantt-chart with tickes would be nice, this seems not to be possible by now.</p> 31. BwInf - Runde 1, Aufgabe 2 //martin-thoma.com/31-bwinf-runde-1-aufgabe-2/ Wed, 12 Dec 2012 12:12:58 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/31-bwinf-runde-1-aufgabe-2 <h2>Die Aufgabenstellung</h2> <blockquote>Zum Transport von Geld werden schwer bewachte Geldtransporter eingesetzt. In einem solchen Geldtransporter k&ouml;nnen Koffer mit M&uuml;nzen transportiert werden. Die Koffer enthalten M&uuml;nzen in unterschiedlicher Menge und mit unterschiedlichem Gesamtwert. Entsprechend unterscheiden sich die Koffer in Gewicht und Wert. Da kommt so einiges an Gewicht zusammen. Es ist daher notwendig, den Transporter gleichm&auml;&szlig;ig zu beladen, so dass er nicht zu einer Seite umkippen kann. Unser Transporter hat links und rechts je einen Kofferraum. F&uuml;r jeden Kofferraum lassen sich Gesamtwert und Gesamtgewicht der darin enthaltenen Koffer bestimmen. Damit der Transporter keine Schlagseite bekommt, m&uuml;ssen die Koffer so einger&auml;umt werden, dass die Differenz zwischen den beiden Gesamtgewichten minimal ist. Aus versicherungstechnischen Gr&uuml;nden d&uuml;rfen die beiden Gesamtwerte sich au&szlig;erdem um h&ouml;chstens 10.000 Euro unterscheiden.</blockquote> <blockquote>Schreibe ein Programm zur Verteilung der Geldkoffer auf die beiden Kofferr&auml;ume. &Uuml;berpr&uuml;fe dein Programm mit den auf <a href="http://www.bundeswettbewerb-informatik.de/index.php?id=1168">www.bundeswettbewerb-informatik.de</a> abgelegten Beispielen mit Angaben zu Werten und Gewichten der einzelnen Koffer.</blockquote> <p>Quelle: <a href="http://www.bundeswettbewerb-informatik.de/fileadmin/templates/bwinf/aufgaben/bwinf31/Aufgabenblatt311_Aufgaben.pdf">www.bundeswettbewerb-informatik.de</a></p> <h2>Vollst&auml;ndiger Pseudocode</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/12/pseudocode-31.1.2-bwinf.png"><img src="../images/2012/12/pseudocode-31.1.2-bwinf.png" alt="Pseudocode zum 31. BwInf, Runde 1, Aufgabe 2" width="" height="" class="size-full wp-image-46861" /></a><p class="wp-caption-text">Pseudocode zum 31. BwInf, Runde 1, Aufgabe 2</p></div> <h2>L&ouml;sung mit GLPK</h2> <p>Der folgende Code muss als partition.mod gespeichert werden:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">/* PARTITION */ /* Written in GNU MathProg by Martin Thoma &lt;info@martin-thoma.de&gt; */ /* Given a set of items I = {1,...,m} with weight w[i] &gt; 0, the PARTITION problem is to split the set of items into two sets such that the absolute value of the difference of the sum of weights of the two sets is minimal */ param m, integer, &gt; 0; /* number of items */ set I := 1..m; /* set of items */ param w{i in 1..m}, &gt; 0; /* w[i] is weight of item i */ param v{i in 1..m}, &gt; 0; /* v[i] is value of item i */ param c, &gt; 0; /* maximum value difference */ param z{i in I, j in 1..m} := /* z[i,j] = 1 if item i is in bin j, otherwise z[i,j] = 0 */ if i = 1 and j = 1 then 1 /* put item 1 into bin 1 */ else if exists{jj in 1..j-1} z[i,jj] then 0 /* if item i is already in some bin, do not put it into bin j */ else if sum{ii in 1..i-1} w[ii] * z[ii,j] + w[i] &gt; c then 0 /* if item i does not fit into bin j, do not put it into bin j */ else 1; /* otherwise put item i into bin j */ check{i in I}: sum{j in 1..2} z[i,j] = 1; /* each item must be exactly in one bin */ param n := 2; display n; set J := 1..n; /* set of bins */ var x{i in I, j in J}, binary; /* x[i,j] = 1 means item i is in bin j */ s.t. one{i in I}: sum{j in J} x[i,j] = 1; /* each item must be exactly in one bin */ /* analog zu http://lists.gnu.org/archive/html/help-glpk/2007-08/msg00036.html */ s.t. lim1{j in J}: (sum{i in I} v[i] * x[i,1]) - (sum{i in I} v[i] * x[i,2]) &lt;= c; s.t. lim2{j in J}: (sum{i in I} v[i] * x[i,2]) - (sum{i in I} v[i] * x[i,1]) &lt;= c; /* the difference of the values may not be more than 10000 */ s.t. lim3{j in J}: (sum{i in I} w[i] * x[i,1]) - (sum{i in I} w[i] * x[i,2]) &gt;= 0; minimize obj: (sum{i in I} w[i] * x[i,1]) - (sum{i in I} w[i] * x[i,2]); /* No abs because of linearity: http://old.nabble.com/How-to-get-a-variable&#39;s-absolute-value-with-GNU-mathprog-tt22241565.html*/ /* objective is to minimize the difference of weights */ data; /* The optimal solution is 3 bins */ /*param m := 15; param v := 1 96000, 2 126000, 3 115000, 4 125000, 5 123000, 6 123000, 7 112000, 8 111000, 9 110000, 10 110000, 11 120000, 12 98000, 13 130000, 14 87000, 15 97000; param w := 1 27, 2 21, 3 27, 4 15, 5 19, 6 46, 7 47, 8 32, 9 14, 10 20, 11 50, 12 19, 13 22, 14 50, 15 46; param m := 20; param w := 1 27, 2 50, 3 19, 4 19, 5 22, 6 79, 7 32, 8 19, 9 75, 10 32, 11 43, 12 82, 13 18, 14 24, 15 20, 16 30, 17 24, 18 80, 19 49, 20 15; param v := 1 276000, 2 745000, 3 585000, 4 585000, 5 723000, 6 808000, 7 552000, 8 584000, 9 626000, 10 551000, 11 423000, 12 944000, 13 496000, 14 133000, 15 633000, 16 461000, 17 813000, 18 855000, 19 695000, 20 406000; param m := 30; param w := 1 103, 2 100, 3 95, 4 119, 5 148, 6 165, 7 721, 8 89, 9 89, 10 156, 11 181, 12 93, 13 239, 14 173, 15 87, 16 113, 17 1816, 18 107, 19 128, 20 102, 21 102, 22 115, 23 118, 24 124, 25 244, 26 394, 27 100, 28 92, 29 103, 30 126; param v := 1 42000, 2 31000, 3 20000, 4 20000, 5 20000, 6 20000, 7 180000, 8 9000, 9 9000, 10 18000, 11 18000, 12 28000, 13 28000, 14 17000, 15 121000, 16 14000, 17 579000, 18 13000, 19 13000, 20 12000, 21 12000, 22 12000, 23 12000, 24 12000, 25 33000, 26 65000, 27 22000, 28 11000, 29 11000, 30 11000; */ param m := 40; param w := 1 3512, 2 87, 3 87, 4 90, 5 91, 6 91, 7 99, 8 218, 9 89, 10 91, 11 91, 12 92, 13 92, 14 93, 15 95, 16 99, 17 100, 18 263, 19 88, 20 89, 21 91, 22 92, 23 93, 24 97, 25 99, 26 99, 27 90, 28 97, 29 399, 30 298, 31 160, 32 854, 33 132, 34 986, 35 255, 36 88, 37 89, 38 92, 39 97, 40 98; param v := 1 672000, 2 10000, 3 10000, 4 10000, 5 10000, 6 10000, 7 10000, 8 244000, 9 73000, 10 9000, 11 9000, 12 9000, 13 9000, 14 9000, 15 9000, 16 9000, 17 9000, 18 83000, 19 8000, 20 8000, 21 8000, 22 8000, 23 8000, 24 8000, 25 8000, 26 8000, 27 7000, 28 7000, 29 103000, 30 144000, 31 58000, 32 399000, 33 15000, 34 472000, 35 120000, 36 12000, 37 12000, 38 11000, 39 11000, 40 11000; param c := 10000; end;</code></pre></div> <p>Jetzt muss man folgendes ausführen:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">glpsol --output example.out --log example.log --math partition.mod</code></pre></div> <p>Das benötigt für die größte Eingabe etwa 18 Sekunden.</p> <p>Wenn man nun in die example.out schaut, sieht man unter anderem folgendes:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">Problem: partition Rows: 47 Columns: 80 (80 integer, 80 binary) Non-zeros: 640 Status: INTEGER OPTIMAL Objective: obj = 5 (MINimum)</code></pre></div> <p>Die interessante Zahl ist die 5. Das ist das Minimum, das in dieser Aufgabe gesucht war. Wie es zu erreichen ist, sieht man in der Ausgabe darunter.</p> <h2>Weiteres</h2> <p>Man kann das Problem auch als MULTIPROCESSOR SCHEDULING mit zwei Maschinen betrachten (und nicht als PARTITION). Vor ein paar Tagen habe ich gelernt, dass es für MULTIPROCESSOR SCHEDULING auch ein <a href="http://de.wikipedia.org/wiki/Approximationsalgorithmus#PTAS.2FPAS">PAS</a> gibt. Dabei bestimmt man für eine konstante Anzahl an Koffern die optimale aufteilung und verteilt den rest mittels LIST SCHEDULING.</p> How can I clear gedit text search / replace history? //martin-thoma.com/how-can-i-clear-gedit-text-search-replace-history/ Sat, 08 Dec 2012 13:48:28 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-can-i-clear-gedit-text-search-replace-history <p>Start <code>gconf-editor</code>:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gconf-editor</code></pre></div> <p>Go to <code>/apps/gnome-settings/gedit/history-gedit2_search_for_entry</code> and <code>/apps/gnome-settings/gedit/history-gedit2_replace_entry_with</code> and remove the content there:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/12/gedit-remove-text-search-history.png"><img src="../images/2012/12/gedit-remove-text-search-history.png" alt="gedit: Clear text search / replace history" width="" height="" class="size-full wp-image-50181" /></a><p class="wp-caption-text">gedit: Clear text search / replace history</p></div> TOP 5: Worst Website Designs //martin-thoma.com/top-5-worst-website-designs/ Fri, 07 Dec 2012 08:27:28 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/top-5-worst-website-designs <p>Here are some screenshots of the worst websites I have ever seen. Most of them use too many colors, something moves or the background is black. One uses frames.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/dokimos-300x210.png"><img src="../images/2012/12/dokimos-300x210.png" alt="dokimos" width="" height="" class="size-medium wp-image-50041" /></a><p class="wp-caption-text"><a href="http://www.dokimos.org/ajff/">dokimos</a></p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/fabricland.co_.uk_-300x214.png"><img src="../images/2012/12/fabricland.co_.uk_-300x214.png" alt="fabricland.co.uk" width="" height="" class="size-medium wp-image-50051" /></a><p class="wp-caption-text"><a href="http://www.fabricland.co.uk/">fabricland.co.uk</a></p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/coolmath-games-300x214.png"><img src="../images/2012/12/coolmath-games-300x214.png" alt="Coolmath-Games" width="" height="" class="size-medium wp-image-50031" /></a><p class="wp-caption-text"><a href="http://coolmath-games.com/">Coolmath-Games</a></p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/ronoslund-300x214.png"><img src="../images/2012/12/ronoslund-300x214.png" alt="ronoslund" width="" height="" class="size-medium wp-image-50061" /></a><p class="wp-caption-text"><a href="http://ronoslund.com/">ronoslund</a></p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/12/5safepoints-300x214.png"><img src="../images/2012/12/5safepoints-300x214.png" alt="5safepoints" width="" height="" class="size-medium wp-image-50071" /></a><p class="wp-caption-text"><a href="http://www.5safepoints.com/">5safepoints</a></p></div> <p>Do you know similar examples for bad website designs (Spambots might have a higher success rate for useful comments now. I’ll have to check that ;-) )</p> Wie zeige ich Differenzierbarkeit? //martin-thoma.com/wie-zeige-ich-differenzierbarkeit/ Wed, 05 Dec 2012 11:59:08 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-zeige-ich-differenzierbarkeit <p>Weil das Thema so wichtig ist und man es doch recht leicht vergisst:</p> <div class="definition">Sei `$I \subseteq \mathbb{R}$` ein Intervall und `$f:I \rightarrow \mathbb{R}$` eine Funktion. <ol> <li>`$f$` hei&szlig;t in `$x_0 \in I$` <strong>differenzierbar</strong> `$\displaystyle :\Leftrightarrow \lim_{x \rightarrow x_0} \frac{f(x) - f(x_0)}{x-x_0}$` existiert und ist in `$\mathbb{R}$`.<br /> In diesem Fall hei&szlig;t `$\displaystyle f'(x_0) = \lim_{x \rightarrow x_0} \frac{f(x) - f(x_0)}{x-x_0}$` die <strong>Ableitung von `$f$` in `$x_0$`</strong>.</li> <li>`$f$` hei&szlig;t auf `$I$` differenzierbar `$:\Leftrightarrow \forall x \in I: f \text{ ist in } x$` differenzierbar.<br /> In diesem Fall wird durch `$x \mapsto f'(x)$` eine Funktion `$f':I \rightarrow \mathbb{R}$` definiert, die <strong>Ableitung</strong> von `$f$` auf `$I$`.</li> </ol> </div> <p>Und wie zeigt man die Existenz dieses Grenzwertes? Das ist eine andere Frage :-P Man sollte sich vielleicht nochmal den Artikel <a href="../konvergenz-von-folgen/">Konvergenz von Folgen</a> bzw. <a href="../konvergenz-von-reihen/">Konvergenz von Reihen</a> anschauen.</p> <p>Ach ja, man kann auch zeigen, dass <code>$\displaystyle \lim_{h \rightarrow 0} \frac{f(x_0+h)-f(x_0)}{h}$</code> existiert und in <code>$\mathbb{R}$</code> ist. Das ist äquivalent.</p> Reflecting a point over a line //martin-thoma.com/reflecting-a-point-over-a-line/ Sun, 02 Dec 2012 15:32:41 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/reflecting-a-point-over-a-line <p>It’s astonishing how difficult it is to find a good explanation how to reflect a point over a line that does not use higher math methods. So here is my explanation:</p> <p>You have a point <code>$P = (x,y)$</code> and a line <code>$g(x) = m \cdot x + t$</code> and you want to get the point <code>$P' = (x', y')$</code> that got mirrored over <code>$g$</code>.</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/12/line-reflection.png"><img src="../images/2012/12/line-reflection.png" alt="Reflection point over a line" width="" height="" class="size-full wp-image-49811" /></a><p class="wp-caption-text">Reflection point over a line</p></div> <p>As you can see, you can construct this quite easily on paper:</p> <ol> <li>Construct the perpendicular through `$P$` to `$g$`. It starts in `$L$` and ends in `$P$`.</li> <li>Double the length of the perpendicular in the direction of `$L$`.</li> <li>The endpoint is `$P'$`.</li> </ol> <p>How can you do that without drawing it?</p> <p>First you have to get the perpendicular <code>$s(x) = m_s \cdot x + t$</code> (the dashed red line).</p> <p>You have to know this: <code>$m_s = - \frac{1}{m}$</code> And then you know that <code>$P$</code> is on <code>$s$</code>. So you simply put in the values <code>$x,y$</code> of P and solve to <code>$t$</code>: <code>$t = y - m_s \cdot x$</code></p> <p>Now you have <code>$s$</code>. As <code>$s$</code> and <code>$g$</code> have exactly point in common, the following equation gives exactly one result:</p> <p><code>$s(x) = g(x)$</code></p> <p>You have to solve for <code>$x$</code>. Then you only need to put <code>$x$</code> into <code>$s(x)$</code> or <code>$g(x)$</code> and you’re done. You’ve calculated <code>$L = (x,y)$</code>.</p> <p>Now you know <code>$\Delta x = |x_L - x_P|$</code> and <code>$\Delta y = |y_L - y_P|$</code> and you can calculate <code>$P'$</code></p> Profiling C programs //martin-thoma.com/profiling-c-programs/ Sat, 01 Dec 2012 17:00:58 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/profiling-c-programs <p>If you have a working program and you want to improve its execution speed, you might want to profile it. An easy way to do so, is adding global variables, increasing them at interesting points and counting how often these points are executed. A more sophisticated way is using a profiler.</p> <h2>valgrind and kcachegrind</h2> <p>Install valgrind and kcachegrind. For Ubuntu users:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install valgrind kcachegrind</code></pre></div> <p>Create a profile:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">valgrind --tool<span class="o">=</span>callgrind ./connectfour</code></pre></div> <p>(I’ve profiled a connect four application. Replace that with your application) This command will create a file called similar to “callgrind.out.4846”.</p> <p>Take a look at the profile:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">kcachegrind callgrind.out.4846</code></pre></div> <p>You can also create a call-graph:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/11/call-graph2.png"><img src="../images/2012/11/call-graph2.png" alt="Call graph of connect four game graph creation program" width="" height="" class="size-full wp-image-49691" /></a><p class="wp-caption-text">Call graph of connect four game graph creation program</p></div> <p>Just take a look at it by yourself. You will see much more than I could tell you now.</p> Debugging a C program //martin-thoma.com/debugging-a-c-program/ Fri, 30 Nov 2012 17:00:15 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/debugging-a-c-program <p>As I began with programming C, I had enormous difficulties to produce working code. Most of the time it didn’t even compile, but when it compiled and I got a runtime error, I basically read my whole code again. I <strike>didn't</strike> don’t know any good online resource for C, so I’ve always searched with Google for answers to questions that I couldn’t properly formulate. One question that is important for beginners is <a href="http://stackoverflow.com/q/12949290/562769">How do I find missing C header files (without Internet)?</a> and another one might be: How can I debug my programs?</p> <h2>Compile time vs. runtime</h2> <p>A typical C workflow looks like this: You have an idea, you write your code, you compile it and you run it.</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/11/c-workflow.png"><img src="../images/2012/11/c-workflow.png" alt="C workflow" width="" height="" class="size-full wp-image-49641" /></a><p class="wp-caption-text">C workflow</p></div> <p>You might make multiple errors. Simple typos or syntax errors are almost always detected at compile time. They are called “compile time errors”. Others, like the access of an array-index that isn’t in the array might only occur sometimes at runtime, depending on the input. Those are runtime errors and they are much more difficult to detect. Additionally, they can not be reproduced that easily as compile time errors can.</p> <h2>gdb</h2> <p>If you want to find runtime errors, you should deactivate all optimization flags and add debugging symbols. A gcc call might look like this:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gcc mySourceFile.c -g</code></pre></div> <p>This produces a binary file called “a.out”.</p> <p>Now should run gdb - GNU debug:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gdb ./a.out</code></pre></div> <p>Within the command line program GNU debug you have to enter:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">run ./a.out</code></pre></div> <p>You should now be able to see the line in which the runtime-error occurs.</p> <h2>valgrind</h2> <p>You might want to give valgrind a try.</p> <p><em>Uninitialised value was created by a stack allocation at 0x80488BC</em>: This could mean that you used an uninitialized variable. Check your variable initializations from the given point. Add <code>--track-origins=yes&lt;/code and run valgrind again.</code></p> Make your Bash more useful //martin-thoma.com/make-your-bash-more-useful/ Thu, 29 Nov 2012 11:15:56 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/make-your-bash-more-useful <p>I just had the problem, that the bash prompt of my universities computer I’ve connected to via SSH looked like this: <code>bash-4.0</code>$`</p> <h2>Change the prompt</h2> <p>I think it’s much more useful to see the path you’re currently using. To get the current path in your bash promt, you have to add the following snippet to your <code>.bashrc</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># This will limit the path to 30 characters. PROMPT_COMMAND='if [ ${#PWD} -gt 30 ]; then myPWD=${PWD:0:12}... ${PWD:${#PWD}-15}; else myPWD=$PWD; fi' PS1=&quot;\u@\h \$myPWD$ &quot; </pre></div> </div> </div> <p>(Source: <a href="http://www.cyberciti.biz/tips/howto-linux-unix-bash-shell-setup-prompt.html">cyberciti.biz</a>)</p> <p>Reload your bash config with <code>source .bashrc</code> and you should instantly see the changes.</p> <h2>Aliases</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># Add color to ls alias ls=&quot;ls --color&quot; </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre># simply update an svn-repository alias swt='svn up /home/moose/Studium/SWT' </pre></div> </div> </div> Karlsruhe: Oberbürgermeisterwahl 2012 //martin-thoma.com/karlsruhe-oberburgermeisterwahl-2012/ Tue, 27 Nov 2012 14:17:39 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/karlsruhe-oberburgermeisterwahl-2012 <p>Da ich mein Erstwohnsitz inzwischen Karlsruhe ist, darf ich hier wählen. Am Sonntag, den 2. Dezember 2012 ist die Wahl des Oberbürgermeisters in Karlsruhe. Seit 1970 wird dieses Amt von einem CDU’ler besetzt.<small><sup><a href="#ref1" name="anchor1">[1]</a></sup></small> <a href="http://de.wikipedia.org/wiki/Heinz_Fenrich">Heinz Fenrich</a> (CDU) ist seit 1998 im Amt, hat aber die Altersgrenze erreicht und kann somit nicht wieder gewählt werden.</p> <h2>Die Kandidaten</h2> <p>Die UStA hat den 7 Kandidaten einige Fragen gestellt und kurze Informationen bereitgestellt (<a href="http://www.usta.de/wiki/buergermeisterwahl2012">Link</a> - Vielen Dank dafür!).</p> <p>Hier mal das Interessanteste:</p> <h3>Dr. Frank Mentrup, SPD-Gr&uuml;ne-KAL</h3> <table class="wikitable"> <tr><td>Alter</td><td>48 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>seit 2007</td></tr> <tr><td>Beruf</td><td>Arzt f&uuml;r Kinder- und Jugendpsychiatrie</td></tr> <tr><td>Politik</td><td>viel, vgl. Wikipedia<br />2011: Staatssekret&auml;r im Ministerium f&uuml;r Kultus, Jugend und Sport</td></tr> <tr><td>Wikipedia</td><td><a href="http://de.wikipedia.org/wiki/Frank_Mentrup">Link</a></td></tr> </table> <p>Ziele und Aussagen:</p> <ul> <li><strong>Wohnraummangel</strong>: &bdquo;[...] werde ich ein kommunales Wohnraumf&ouml;rderungsprogramm f&uuml;r Karlsruhe erarbeiten&ldquo;</li> <li><strong>Studiticket</strong>: viel bla bla, durchaus gute und vern&uuml;nftige Begr&uuml;ndungen, aber in kurz: An den Preisen f&uuml;r das Studiticket kann der OB nichts machen</li> <li><strong>Rad vs. Baustellen</strong>: &bdquo;Der weitere Ausbau von Radwegen, insbesondere auch auf studentischen Routen wie z.B. zwischen Wohnheimen und den Hochschulen muss z&uuml;gig erfolgen.&ldquo;</li> <li><strong>Slacklinen</strong>: &bdquo;[ich werde] mich f&uuml;r die Einrichtung von Slacklineanlagen einsetzen.&ldquo;</li> <li><strong>Sonstiges</strong>: Als Oberb&uuml;rgermeister werde ich eine ausgewogene Stadtentwicklungspolitik verfolgen, die Karlsruhe zu einer gr&uuml;nen Stadt machen wird mit einem durchgehenden Gr&uuml;nstreifen vom Rhein bis in die Bergd&ouml;rfer.</li> </ul> <p>Insgesamt erwecken Mentrup einen soliden Eindruck. Die Antworten scheinen durchdacht zu sein und er spricht einige Projekte / Initiativen an, die es bereits gibt. Er scheint also mit der Politik der Stadt vertraut zu sein.</p> <h3>Ingo Wellenreuther, CDU</h3> <table class="wikitable"> <tr><td>Alter</td><td>52 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>geboren</td></tr> <tr><td>Beruf</td><td>11 Jahre Richter am Landgericht und Oberlandgericht</td></tr> <tr><td>Politik</td><td>viel, vgl. Wikipedia<br />seit &uuml;ber 10 Jahren Bundestagsabgeordneter<br />seit dreizehn Jahren im Stadtrat</td></tr> <tr><td>Wikipedia</td><td><a href="http://de.wikipedia.org/wiki/Ingo_Wellenreuther">Link</a></td></tr> </table> <p>Ziele und Aussagen:</p> <ul> <li><strong>Wohnraummangel</strong>: &bdquo;[ich will] gezielt auf die Umlandgemeinden zugehen, [...] damit auch diese Wohnraum f&uuml;r Studenten schaffen&ldquo;</li> <li><strong>Studiticket</strong>: &bdquo;Als Oberb&uuml;rgermeister w&uuml;rde ich mich f&uuml;r ein studierendenfreundliches Ergebnis stark machen.&ldquo;</li> <li><strong>Rad vs. Baustellen</strong>: Sehr viel blah blah</li> <li><strong>Slacklinen</strong>: &bdquo;[ich werde] mich beim Land f&uuml;r deren offizielle Genehmigung stark machen&ldquo;</li> <li><strong>Sonstiges</strong>: &bdquo;Eine Vergr&ouml;&szlig;erung des KIT-Campus S&uuml;d auf dem Gel&auml;nde des Wildparkstadions halte ich f&uuml;r dringend notwendig. Dies w&uuml;rde durch einen <u>Stadionneubau in Autobahnn&auml;he</u> m&ouml;glich, f&uuml;r den ich mich seit vielen Jahren einsetze und der auch viele andere Probleme l&ouml;sen w&uuml;rde.&ldquo;</li> </ul> <h3>Fostiropoulos, Linke</h3> <table class="wikitable"> <tr><td>Alter</td><td>54 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>Architektur studiert</td></tr> <tr><td>Beruf</td><td>Unternehmen im Bereich der beruflichen Weiterbildung</td></tr> <tr><td>Politik</td><td>seit 12 Jahren Stadtrat</td></tr> </table> <p>Ziele und Aussagen:</p> <ul> <li><strong>Wohnraummangel</strong>: setzt sich f&uuml;r ein kommunale Wohnungsprogramm ein</li> <li><strong>Studiticket</strong>: &bdquo;&Ouml;PNV kostenlos und &uuml;ber Steuermittel finanziert&ldquo;</li> <li><strong>Rad vs. Baustellen</strong>: nichts konkretes</li> <li><strong>Slacklinen</strong>: &bdquo;Daf&uuml;r ist das Land zust&auml;ndig.&ldquo;</li> <li><strong>Sonstiges</strong>: Kostenfreie Kindertagesst&auml;tten f&uuml;r alle Kinder von 1 bis 6, kommunales Wohnungsprogramm</li> </ul> <h3>Friedemann Kalmbach, W&auml;hlerliste</h3> <table class="wikitable"> <tr><td>Alter</td><td>58 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>?</td></tr> <tr><td>Beruf</td><td>Technischer Zeichner in einer Maschinenbaufabrik<br />Gymnasiallehrer (Physik, Geographie)</td></tr> <tr><td>Politik</td><td>seit 2009 tr&auml;gt er politische Verantwortung im Gemeinderat</td></tr> </table> <p>Ziele und Aussagen:</p> <ul> <li><strong>Wohnraummangel</strong>: kommunales Wohnungsbauprogramm, Investoren, B&uuml;rofl&auml;chen in Wohnraum umwandeln</li> <li><strong>Studiticket</strong>: &bdquo;[Ich werde] den Druck auf den KVV deutlich erh&ouml;hen, um eine moderatere Preisgestaltung zu erzielen.&ldquo;</li> <li><strong>Rad vs. Baustellen</strong>: Nichts konkretes</li> <li><strong>Slacklinen</strong>: ist nicht Sache des OB</li> <li><strong>Sonstiges</strong>: -</li> </ul> <h3>J&uuml;rgen Wenzel, freie W&auml;hler Karlsruhe</h3> <table class="wikitable"> <tr><td>Alter</td><td>50 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>geboren</td></tr> <tr><td>Beruf</td><td>studierte klassische Malerei und Zeichnen<br />arbeitete als Comiczeichner, Gestalter von Plattencovern und Werbeanzeigen</td></tr> <tr><td>Politik</td><td>seit 2009 im Gemeinderat</td></tr> </table> <h3>Sascha Oehme, Unabh&auml;ngiger Kandidat</h3> <table class="wikitable"> <tr><td>Alter</td><td>42 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>?</td></tr> <tr><td>Beruf</td><td>Logistikmeister</td></tr> <tr><td>Politik</td><td>&ouml;ffentlichen Wohnbau, Abschaffung der Hundesteuer, freies W-LAN</td></tr> <tr><td>Wikipedia</td><td><a href="http://de.wikipedia.org/wiki/Ingo_Wellenreuther">Link</a></td></tr> </table> <h3>Michael B&ouml;hm, Unabh&auml;ngiger Kandidat</h3> <p>alias „Herr Kruscht“</p> <table class="wikitable"> <tr><td>Alter</td><td>49 Jahre</td></tr> <tr><td>In Karlsruhe</td><td>geboren (Eggstein)</td></tr> <tr><td>Beruf</td><td>Entr&uuml;mpler<br />Besitzer eines Blechdosenmuseums</td></tr> <tr><td>Politik</td><td>&ouml;ffentlichen Wohnbau, Abschaffung der Hundesteuer, freies W-LAN</td></tr> <tr><td>Wikipedia</td><td><a href="http://de.wikipedia.org/wiki/Ingo_Wellenreuther">Link</a></td></tr> </table> <p>Ist gegen die U-Bahn, möchte das Karlsruher Rathaus auf den Werderplatz bauen. „Das jetzige Rathaus soll eine Kindertagesstätte werden und die Südstadt eine eigenständige Stadt.“ Herabsenkung des Wahlalters auf 16 Jahre.</p> <h2>Prognosen</h2> <ul> <li>48,22%: Mentrup, SPD-GR&Uuml;-KAL</li> <li>38,16%: Wellenreuther, CDU</li> <li>04,18%: Fostiropoulos, Linke</li> <li>04,05%: Kalmbach, GfK</li> <li>03,00%: Wenzel, FW</li> <li>02,39%: Oehme</li> <li>00,68%: Kruscht</li> </ul> <p>Quelle: <a href="http://ka-news.wahlfieber.de/de_du/markt/D-2012-KA-BM1--oberburgermeisterwahlen-in-karlsruhe-2012/">kanews.wahlfieber.de</a></p> <h2>Links</h2> <ol> <li><a name="ref1" href="#anchor1">&uarr;</a>: Wikipedia, <a href="http://de.wikipedia.org/wiki/Geschichte_Karlsruhes#.28Ober-.29B.C3.BCrgermeister">Geschichte Karlsruhes</a></li> </ol> Linux Scheduler //martin-thoma.com/linux-scheduler/ Mon, 26 Nov 2012 23:25:15 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/linux-scheduler <div class="info">Der folgende Text wurde von <a href="http://klammler.eu/">Moritz Klammler</a>, einem Informatik-Studenten am KIT, als E-Mail an die interne Mailingliste der Vorlesung geschrieben. Ich habe nur ein paar Kleinigkeiten umformuliert und die Formattierung ge&auml;ndert.</div> <h2>Mailinglisten-Beitrag</h2> <p>Der in der Vorlesung vorgestellte <code>$\mathcal{O}(1)$</code> Scheduler<small><sup><a href="#ref1" name="anchor1">[1]</a></sup></small> wurde vom 2.6er Linux Kernel bis Version 2.6.23 verwendet und dann durch den sogenannten Completely Fair Scheduler (CFS)<small><sup><a href="#ref2" name="anchor2">[2]</a></sup></small> abgelöst, der Rot-Schwarz-Bäume verwendet, und daher in <code>$\mathcal{O}(\log(n))$</code> läuft – dafür aber komplett fair ist ;-) Beide Scheduler wurden von Ingo Molnár entworfen und größtenteils implementiert. Abgesehen von den Wikipedia Artikeln fand ich auch Ingos eigene Beschreibung<small><sup><a href="#ref3" name="anchor1">[3]</a></sup></small> sehr interessant. In der prä-2.6-Ära des Linux Kernels wurde ein Scheduler verwendet, zu dessen Effizienz ich keine Angaben gefunden habe. Anhand der (ziemlich detaillierten) Beschreibung in Kapitel 10 von „Understanding the Linux Kernel“<small><sup><a href="#ref4" name="anchor4">[1]</a></sup></small> gehe ich jedoch davon aus, dass es <code>$\mathcal{O}(n)$</code> gewesen sein muss. Auch wenn die dort beschriebenen Algorithmen inzwischen mehrfach überholt sind, fand ich das Kapitel sehr lesenswert.</p> <p>Wie in der Vorlesung vermutet wurde, kann man den Scheduler natürlich konfigurieren. Dazu ist es aber nicht notwendig, neu zu kompilieren – noch nicht einmal neu zu booten. Stattdessen kann man (beim CFS) einfach über das /proc Dateisystem in die verschiedenen Dateien in</p> <p><code>/proc/sys/kernel/...</code></p> <p>schreiben. Die Änderungen werden instantan wirksam. (Und spätestens zum nächsten Reboot wieder zurückgesetzt, man kann also nicht viel kaputt machen.) Permanente Änderungen kann man in <code>/etc/sysctl.conf</code> schreiben. (Habe ich noch nicht probiert.)</p> <p>Ich habe ein kleines Programm geschrieben, das sehr viele Subprozesse erzeugt, die alle sinnlose Rechnungen auf der CPU ausführen und zwischendurch in regelmäßigen Intervallen eine (eigentlich zwei) Zellen auf dem Terminal umfärben. Man kann anhand dessen, wie sich das Muster ändert, schön sehen, wie oft ein einzelner Prozess an die Reihe kommt, und wie lange er es bleibt, wenn er es einmal ist. Das Programm kann von <a href="http://klammler.eu/data/computer-science/kit/os/blink-1.0.tar.gz">meiner Website</a> heruntergeladen werden. In dem Archiv ist auch ein kleines Shell-Skript, <code>sched-tune.sh</code>, mit dem man die wichtigsten Parameter ändern kann. Die README Datei in dem Archiv erklärt genauer, wie man das Programm benutzen kann.</p> <p>Da der Bildschirm beim Ausführen des Programms (gewollt) stark flackert, muss ich Epileptikern und anderen empfindlichen Personen unter Umständen leider davon abraten.</p> <p>Leider lässt der Kernel keine völlig unsinnigen Werte zu. Man kann also nur bedingt ausprobieren, welchen Einfluss extreme Einstellungen haben / hätten. Wie in Referenz 4 beschrieben, „friert“ die grafische Oberfläche übrigens auch nicht ein, wenn man größere Scheduling Intervalle wählt, da jeder Tastendruck einen Interrupt auslöst, der – egal wie geschedulet wird – immer die Kontrolle an jenen Prozess übergibt, der gerade das Keyboard „gegrabbt“ hat.</p> <p>Grüße</p> <p>Moritz</p> <h2>Video</h2> <p>Ich habe mal ein Video von Moritz’ Programm gemacht:</p> <iframe width="420" height="315" src="http://www.youtube.com/embed/DOOrbrcM3YU" frameborder="0" allowfullscreen=""></iframe> <h2>Referenzen</h2> <p>[1] <a name="ref1" href="#anchor1">↑</a>: „<a href="http://en.wikipedia.org/wiki/O%281%29_scheduler">O(1) Scheduler</a>“ in: Wikipedia, the free encyclopedia. Abgerufen am 13. November 2012. <br /> [2] <a name="ref2" href="#anchor2">↑</a>: „<a href="http://en.wikipedia.org/wiki/Completely_Fair_Scheduler">Completely Fair Scheduler</a>“ in: Wikipedia, the free encyclopedia. Abgerufen am 13. November 2012. [3] <a name="ref3" href="#anchor3">↑</a>: Ingo Molnár, „<a href="http://people.redhat.com/mingo/cfs-scheduler/sched-design-CFS.txt">This is the CFS scheduler</a>“. Abgerufen am 13. November 2012. [4] <a name="ref4" href="#anchor4">↑</a>: Daniel P. Bovet und Marco Cesati, „<a href="http://oreilly.com/catalog/linuxkernel/chapter/ch10.html">Understanding the Linux Kernel</a>“. O’Reilly, 2000, abgerufen am 13. November 2012.</p> Tribonacci-Folge //martin-thoma.com/tribonacci-folge/ Mon, 19 Nov 2012 20:52:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/tribonacci-folge <p>Folgende Aufgabe gab es (sinngemäß) für das Modul „Programmieren“ im zweiten Übungsblatt 2012:</p> <p>Sei <code>$(a_n)_{n \in \mathbb{N}}$</code> eine Folge und definiert durch:</p> <p><code>$a_n := \begin{cases} 1 &amp;\text{, falls } n \in \{0,1,2\}\\ a_{n-1} + a_{n-2} + a_{n-3} &amp; \text{, falls } n \geq 3 \end{cases}$</code>.</p> <p>Ich werde im folgenden mal kurz mögliche Lösungen in Python (und eine in Java) vorstellen. Python hat bei solchen Aufgaben den Vorteil, dass es viel kompakter ist und Ganzzahlen beliebig groß werden können.</p> <h2>H&auml;ndische L&ouml;sung</h2> <p>Bevor man irgendwas programmiert, sollte man sicherstellen, dass man es testen kann. Was wären also die ersten paar Folgenglieder?</p> <p><code>$a_0 = a_1 = a_2 = 1, a_3 = 3, a_4 = 5, a_5 = 9, a_6 = 17, a_7 = 31, a_8 = 57$</code></p> <h2>Rekursive L&ouml;sung</h2> <p>Solche Aufgaben lassen sich häufig sehr einfach rekursiv lösen:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">tribonacci</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="mi">3</span><span class="p">:</span> <span class="k">return</span> <span class="n">n</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="n">tribonacci</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">tribonacci</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">2</span><span class="p">)</span> <span class="o">+</span> <span class="n">tribonacci</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">3</span><span class="p">)</span></code></pre></div> <p>Allerdings hat diese rekursive Lösung den riesigen nachteil, dass viele Berechnungen redundant sind. Angenommen, wir wollen <code>tribonacci(5)</code> berechnen. Dann läuft folgendes ab:</p> <ol> <li>Aufruf <code>tribonacci(5)</code> <ol> <li>Aufruf <code>tribonacci(4)</code> <ol> <li>Aufruf <code>tribonacci(3)</code> <ol> <li>Aufruf <code>tribonacci(2)</code> <li>Aufruf <code>tribonacci(1)</code> <li>Aufruf <code>tribonacci(0)</code> </li> <li>Aufruf <code>tribonacci(2)</code></li> <li>Aufruf <code>tribonacci(1)</code></li> </li> <li>Aufruf <code>tribonacci(3)</code> <ol> <li>Aufruf <code>tribonacci(2)</code> <li>Aufruf <code>tribonacci(1)</code> <li>Aufruf <code>tribonacci(0)</code> </li> <li>Aufruf <code>tribonacci(2)</code> </li> Man sieht deutlich, dass z.B. <code>tribonacci(3)</code> mehrfach berechnet werden muss. Wie kann man so was verbessern? <h2>Bottom-Up Ansatz</h2> Wir ben&ouml;tigen f&uuml;r ein neues Folgenglied immer nur das vorhergehende. Das kann dann so aussehen: <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">tribonacciBottomUp</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">last</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">secondLast</span> <span class="o">=</span> <span class="mi">1</span> <span class="n">thirdLast</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span><span class="n">n</span><span class="p">):</span> <span class="n">new</span> <span class="o">=</span> <span class="n">last</span> <span class="o">+</span> <span class="n">secondLast</span> <span class="o">+</span> <span class="n">thirdLast</span> <span class="n">thirdLast</span> <span class="o">=</span> <span class="n">secondLast</span> <span class="n">secondLast</span> <span class="o">=</span> <span class="n">last</span> <span class="n">last</span> <span class="o">=</span> <span class="n">new</span> <span class="k">return</span> <span class="n">last</span></code></pre></div> <h2>Fill it</h2> Eine weitere M&ouml;glichkeit w&auml;re die schw&auml;che des rekursiven Ansatzes zu eliminieren, indem man alle bisher berechneten Werte in einem Array speichert. <h2>Wertetabelle</h2> <table> <tr><th>i</th><th>a_i</th></tr> <tr><td>0</td><td>1</td></tr> <tr><td>1</td><td>1</td></tr> <tr><td>2</td><td>1</td></tr> <tr><td>3</td><td>3</td></tr> <tr><td>4</td><td>5</td></tr> <tr><td>5</td><td>9</td></tr> <tr><td>6</td><td>17</td></tr> <tr><td>7</td><td>31</td></tr> <tr><td>8</td><td>57</td></tr> <tr><td>9</td><td>105</td></tr> <tr><td>10</td><td>193</td></tr> <tr><td>11</td><td>355</td></tr> <tr><td>12</td><td>653</td></tr> <tr><td>13</td><td>1201</td></tr> <tr><td>14</td><td>2209</td></tr> <tr><td>15</td><td>4063</td></tr> <tr><td>16</td><td>7473</td></tr> <tr><td>17</td><td>13745</td></tr> <tr><td>18</td><td>25281</td></tr> <tr><td>19</td><td>46499</td></tr> <tr><td>20</td><td>85525</td></tr> <tr><td>21</td><td>157305</td></tr> <tr><td>22</td><td>289329</td></tr> <tr><td>23</td><td>532159</td></tr> <tr><td>24</td><td>978793</td></tr> <tr><td>25</td><td>1800281</td></tr> <tr><td>26</td><td>3311233</td></tr> <tr><td>27</td><td>6090307</td></tr> <tr><td>28</td><td>11201821</td></tr> <tr><td>29</td><td>20603361</td></tr> <tr><td>30</td><td>37895489</td></tr> <tr><td>31</td><td>69700671</td></tr> <tr><td>32</td><td>128199521</td></tr> <tr><td>33</td><td>235795681</td></tr> <tr><td>34</td><td>433695873</td></tr> <tr><td>35</td><td>797691075</td></tr> <tr><td>36</td><td>1467182629</td></tr> <tr><td>37</td><td>2698569577</td></tr> <tr><td>38</td><td>4963443281</td></tr> <tr><td>39</td><td>9129195487</td></tr> <tr><td>40</td><td>16791208345</td></tr> </table> <h2>Java</h2> Java-Nutzer m&uuml;ssen sich dar&uuml;ber im klaren sein, dass alle Elemente, die gr&ouml;&szlig;er als 36 sind, die <code>int</code>-Grenzen sprengen. Eine L&ouml;sung f&uuml;r das &Uuml;bungsblatt k&ouml;nnte ungef&auml;hr so aussehen: <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="cm">/** This class calculates numbers of the Tribonacci sequence. */</span> <span class="kd">public</span> <span class="kd">final</span> <span class="kd">class</span> <span class="nc">Tribonacci</span> <span class="o">{</span> <span class="cm">/**</span> <span class="cm"> * Utility classes should not have a public or default </span> <span class="cm"> * constructor.</span> <span class="cm"> */</span> <span class="kd">private</span> <span class="nf">Tribonacci</span><span class="o">()</span> <span class="o">{</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Calculate the n&#39;th Element of the Tribonacci sequence (a_n). </span> <span class="cm"> * The sequence is defined as:</span> <span class="cm"> * a_0 = a_1 = a_2 = a</span> <span class="cm"> * a_n = a_(n-1) + a_(n-2) + a_(n-3)</span> <span class="cm"> *</span> <span class="cm"> * @param n the element of the Tribonacci sequence you want to</span> <span class="cm"> * calculate</span> <span class="cm"> * @return the value of the n&#39;th element in the Tribonacci</span> <span class="cm"> * sequence</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">long</span> <span class="nf">calculateTribonacci</span><span class="o">(</span><span class="kd">final</span> <span class="kt">long</span> <span class="n">n</span><span class="o">)</span> <span class="o">{</span> <span class="kt">long</span> <span class="n">last</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="kt">long</span> <span class="n">secondLast</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="kt">long</span> <span class="n">thirdLast</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="kt">long</span> <span class="n">newTri</span> <span class="o">=</span> <span class="n">last</span> <span class="o">+</span> <span class="n">secondLast</span> <span class="o">+</span> <span class="n">thirdLast</span><span class="o">;</span> <span class="n">thirdLast</span> <span class="o">=</span> <span class="n">secondLast</span><span class="o">;</span> <span class="n">secondLast</span> <span class="o">=</span> <span class="n">last</span><span class="o">;</span> <span class="n">last</span> <span class="o">=</span> <span class="n">newTri</span><span class="o">;</span> <span class="o">}</span> <span class="k">return</span> <span class="n">last</span><span class="o">;</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Prints out the Tribonacci number a_36 </span> <span class="cm"> * the (37th Tribonacci number)</span> <span class="cm"> * @param args the command line arguments</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="kd">final</span> <span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">calculateTribonacci</span><span class="o">(</span><span class="mi">36</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> </li></li></ol></li></li></ol></li></ol></li></ol></li></ol> Project Euler: Problem 35 //martin-thoma.com/project-euler-problem-35/ Sat, 17 Nov 2012 13:23:01 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/project-euler-problem-35 <p>The task in <a href="http://projecteuler.net/problem=35">Problem 35</a> of Project Euler is:</p> <blockquote>The number, 197, is called a circular prime because all rotations of the digits: 197, 971, and 719, are themselves prime. There are thirteen such primes below 100: 2, 3, 5, 7, 11, 13, 17, 31, 37, 71, 73, 79, and 97. How many circular primes are there below one million?</blockquote> <h2>How to solve</h2> <p>If you have heard of the sieve of Eratosthenes, this one sounds quite easy:</p> <ol> <li>Find all primes below one million</li> <li>For each prime, do: <ol> <li>Generate all rotations</li> <li>Check for every rotation if it is a prime</li> </ol> </li> <li>Count the number of circular primes</li> </ol> <h2>The implementation</h2> <h3>Sieve of Eratosthenes</h3> <p>The finds all primes below <code>$n \in \mathbb{N}$</code>. But you can make a lot of mistakes in the implementation.</p> <p>First, this is the way the sieve of Eratosthenes works:</p> <div style="width: 455px" class="wp-caption aligncenter"><a href="../images/2012/11/Sieve_of_Eratosthenes_animation.gif"><img src="../images/2012/11/Sieve_of_Eratosthenes_animation.gif" alt="Sieve of Eratosthenes animation" width="" height="" class="size-full" /></a><p class="wp-caption-text">Sieve of Eratosthenes: algorithm steps for primes below 121 (including optimization of starting from prime's square).<br />Source: <a href="http://commons.wikimedia.org/wiki/File:Sieve_of_Eratosthenes_animation.gif">Wikimedia</a></p></div> <p>For example, this implementation is not good:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">getPrimesBelowN</span><span class="p">(</span><span class="n">n</span><span class="o">=</span><span class="mi">1000000</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Sieve of Eratosthenes &quot;&quot;&quot;</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">ceil</span> <span class="n">roundUp</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">,</span> <span class="n">prime</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">ceil</span><span class="p">(</span><span class="nb">float</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">/</span> <span class="n">prime</span><span class="p">))</span> <span class="n">primes</span> <span class="o">=</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="k">for</span> <span class="n">currentPrime</span> <span class="ow">in</span> <span class="n">primes</span><span class="p">:</span> <span class="k">for</span> <span class="n">multiplicant</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">roundUp</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">currentPrime</span><span class="p">)):</span> <span class="n">noPrime</span> <span class="o">=</span> <span class="n">multiplicant</span> <span class="o">*</span> <span class="n">currentPrime</span> <span class="k">if</span> <span class="n">noPrime</span> <span class="ow">in</span> <span class="n">primes</span><span class="p">:</span> <span class="n">primes</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">noPrime</span><span class="p">)</span> <span class="k">return</span> <span class="n">primes</span></code></pre></div> <p>Whats bad with this code? Well, just think about what it does: For every <code>noPrime</code> Python has to go through the whole list. I couldn’t find how <code>in</code> is implemented, but I guess it is linear. So Python has to go through the whole list for <code>in</code>. Additionally, <code>remove</code> could also be expensive.</p> <p>How could this get improved? Here is a better solution:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">getPrimesBelowN</span><span class="p">(</span><span class="n">n</span><span class="o">=</span><span class="mi">1000000</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Sieve of Eratosthenes &quot;&quot;&quot;</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">ceil</span> <span class="n">roundUp</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">,</span> <span class="n">prime</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">ceil</span><span class="p">(</span><span class="nb">float</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">/</span> <span class="n">prime</span><span class="p">))</span> <span class="n">primes</span> <span class="o">=</span> <span class="p">[</span><span class="bp">True</span><span class="p">]</span> <span class="o">*</span> <span class="n">n</span> <span class="n">primes</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="n">primes</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="n">primeList</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">currentPrime</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">primes</span><span class="p">[</span><span class="n">currentPrime</span><span class="p">]:</span> <span class="k">continue</span> <span class="n">primeList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">currentPrime</span><span class="p">)</span> <span class="k">for</span> <span class="n">multiplicant</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">roundUp</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">currentPrime</span><span class="p">)):</span> <span class="n">primes</span><span class="p">[</span><span class="n">multiplicant</span> <span class="o">*</span> <span class="n">currentPrime</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="k">return</span> <span class="n">primeList</span></code></pre></div> <p>This solution does not need to search for <code>noPrime</code>, it simply jumps there in the list.</p> <p>A generator version of the sieve of Erasthostenes can be found on <a href="http://code.activestate.com/recipes/117119-sieve-of-eratosthenes/">code.activestate.com</a>.</p> <h3>isCircularPrime</h3> <p>Rotation the digits of a number is the same as cutting the number into two pieces and switching the position of the pieces:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">isCircularPrime</span><span class="p">(</span><span class="n">primes</span><span class="p">,</span> <span class="n">number</span><span class="p">):</span> <span class="n">number</span> <span class="o">=</span> <span class="nb">str</span><span class="p">(</span><span class="n">number</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">number</span><span class="p">)):</span> <span class="n">rotatedNumber</span> <span class="o">=</span> <span class="n">number</span><span class="p">[</span><span class="n">i</span><span class="p">:</span><span class="nb">len</span><span class="p">(</span><span class="n">number</span><span class="p">)]</span> <span class="o">+</span> <span class="n">number</span><span class="p">[</span><span class="mi">0</span><span class="p">:</span><span class="n">i</span><span class="p">]</span> <span class="k">if</span> <span class="nb">int</span><span class="p">(</span><span class="n">rotatedNumber</span><span class="p">)</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">primes</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span></code></pre></div> <p>Here is the same problem as above, in the sieving algorithm: Searching through the list takes much more time than jumping to a position in the list. So this one is better:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">isCircularPrime</span><span class="p">(</span><span class="n">primes</span><span class="p">,</span> <span class="n">number</span><span class="p">):</span> <span class="n">number</span> <span class="o">=</span> <span class="nb">str</span><span class="p">(</span><span class="n">number</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">number</span><span class="p">)):</span> <span class="n">rotatedNumber</span> <span class="o">=</span> <span class="n">number</span><span class="p">[</span><span class="n">i</span><span class="p">:</span><span class="nb">len</span><span class="p">(</span><span class="n">number</span><span class="p">)]</span> <span class="o">+</span> <span class="n">number</span><span class="p">[</span><span class="mi">0</span><span class="p">:</span><span class="n">i</span><span class="p">]</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">primes</span><span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="n">rotatedNumber</span><span class="p">)]:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span></code></pre></div> <h3>Some more speedups Every prime that contains one of the digits 0, 2, 4, 6 or 8 can't be a circular prime, because one rotation exist where that digit is at the end. This rotation would be divisible by 2 and thus not be a prime (except for 2, of course). You can use the same thought for the digit 5. So you can skip those digits <h3>The final snippet</h3> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">getPrimesBelowN</span><span class="p">(</span><span class="n">n</span><span class="o">=</span><span class="mi">1000000</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;Get all primes below n with the sieve of Eratosthenes. </span> <span class="sd"> @return: a list 0..n with boolean values that indicate if </span> <span class="sd"> i in 0..n is a prime.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">ceil</span> <span class="n">primes</span> <span class="o">=</span> <span class="p">[</span><span class="bp">True</span><span class="p">]</span> <span class="o">*</span> <span class="n">n</span> <span class="n">primes</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="n">primes</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="n">primeList</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">roundUp</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">,</span> <span class="n">prime</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">ceil</span><span class="p">(</span><span class="nb">float</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">/</span> <span class="n">prime</span><span class="p">))</span> <span class="k">for</span> <span class="n">currentPrime</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">primes</span><span class="p">[</span><span class="n">currentPrime</span><span class="p">]:</span> <span class="k">continue</span> <span class="n">primeList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">currentPrime</span><span class="p">)</span> <span class="k">for</span> <span class="n">multiplicant</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">roundUp</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">currentPrime</span><span class="p">)):</span> <span class="n">primes</span><span class="p">[</span><span class="n">multiplicant</span> <span class="o">*</span> <span class="n">currentPrime</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="k">return</span> <span class="n">primes</span> <span class="k">def</span> <span class="nf">isCircularPrime</span><span class="p">(</span><span class="n">primes</span><span class="p">,</span> <span class="n">number</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;Check if number is a circular prime.</span> <span class="sd"> </span> <span class="sd"> Keyword arguments:</span> <span class="sd"> primes -- a list from 0..n with boolean values that indicate if </span> <span class="sd"> i in 0..n is a prime</span> <span class="sd"> number -- the integer you want to check</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="n">number</span> <span class="o">=</span> <span class="nb">str</span><span class="p">(</span><span class="n">number</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">number</span><span class="p">)):</span> <span class="n">rotatedNumber</span> <span class="o">=</span> <span class="n">number</span><span class="p">[</span><span class="n">i</span><span class="p">:</span><span class="nb">len</span><span class="p">(</span><span class="n">number</span><span class="p">)]</span> <span class="o">+</span> <span class="n">number</span><span class="p">[</span><span class="mi">0</span><span class="p">:</span><span class="n">i</span><span class="p">]</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">primes</span><span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="n">rotatedNumber</span><span class="p">)]:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Start sieving.&quot;</span><span class="p">)</span> <span class="n">primes</span> <span class="o">=</span> <span class="n">getPrimesBelowN</span><span class="p">(</span><span class="mi">1000000</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;End sieving.&quot;</span><span class="p">)</span> <span class="n">numberOfPrimes</span> <span class="o">=</span> <span class="mi">2</span> <span class="k">print</span><span class="p">(</span><span class="mi">2</span><span class="p">)</span> <span class="c"># I print them now, because I want to skip all primes</span> <span class="k">print</span><span class="p">(</span><span class="mi">5</span><span class="p">)</span> <span class="c"># that contain one of those digits: 0,2,4,5,6,8</span> <span class="k">for</span> <span class="n">prime</span><span class="p">,</span> <span class="n">isPrime</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">primes</span><span class="p">):</span> <span class="k">if</span> <span class="p">(</span><span class="ow">not</span> <span class="n">isPrime</span><span class="p">)</span> <span class="ow">or</span> <span class="p">(</span><span class="s">&quot;2&quot;</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">prime</span><span class="p">))</span> <span class="ow">or</span> \ <span class="p">(</span><span class="s">&quot;4&quot;</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">prime</span><span class="p">))</span> <span class="ow">or</span> <span class="p">(</span><span class="s">&quot;6&quot;</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">prime</span><span class="p">))</span> <span class="ow">or</span> \ <span class="p">(</span><span class="s">&quot;8&quot;</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">prime</span><span class="p">))</span> <span class="ow">or</span> <span class="p">(</span><span class="s">&quot;0&quot;</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">prime</span><span class="p">))</span> <span class="ow">or</span> \ <span class="p">(</span><span class="s">&quot;5&quot;</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">prime</span><span class="p">)):</span> <span class="k">continue</span> <span class="k">if</span> <span class="n">isCircularPrime</span><span class="p">(</span><span class="n">primes</span><span class="p">,</span> <span class="n">prime</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="n">prime</span><span class="p">)</span> <span class="n">numberOfPrimes</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Number of circular primes: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">numberOfPrimes</span><span class="p">)</span></code></pre></div> It takes about 1.096 seconds (in comparison: having the version of <code>isCircularPrime</code> that searches through the list of primes took over 5 minutes!) </h3> Project Euler: Problem 33 //martin-thoma.com/project-euler-problem-33/ Wed, 14 Nov 2012 15:43:35 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/project-euler-problem-33 <p>The task in <a href="http://projecteuler.net/problem=33">Problem 33</a> of Project Euler is:</p> <blockquote>The fraction `$\frac{49}{98}$` is a curious fraction, as an inexperienced mathematician in attempting to simplify it may incorrectly believe that `$\frac{49}{98} = \frac{4}{8}$`, which is correct, is obtained by cancelling the 9s. We shall consider fractions like, `$\frac{30}{50} = \frac{3}{5}$`, to be trivial examples. There are exactly four non-trivial examples of this type of fraction, less than one in value, and containing two digits in the numerator and denominator. If the product of these four fractions is given in its lowest common terms, find the value of the denominator.</blockquote> <h2>How to solve</h2> <p>The solution to this task is pretty straight forward. As the nominator has to have two digits and the denominator also has to be in [10, 99], we only have about <code>$100 \cdot 100 = 10000$</code> that we have to check.</p> <p>How do we check a given nominator / denominator pair? Well, we can go through each digit of the nominator and check if it is also in the denominator. If it is there, we have to check if the resulting fraction has the same value as before. If it has, we can print it.</p> <h2>My solution</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">isCuriousFraction</span><span class="p">(</span><span class="n">numerator</span><span class="p">,</span> <span class="n">denomiator</span><span class="p">):</span> <span class="k">for</span> <span class="n">digit</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">numerator</span><span class="p">):</span> <span class="k">if</span> <span class="n">digit</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">denomiator</span><span class="p">):</span> <span class="k">for</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span> <span class="ow">in</span> <span class="p">[(</span><span class="n">i</span><span class="p">,</span><span class="n">j</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">2</span><span class="p">)</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">2</span><span class="p">)]:</span> <span class="k">if</span> <span class="nb">str</span><span class="p">(</span><span class="n">numerator</span><span class="p">)[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="n">digit</span> <span class="o">==</span> <span class="nb">str</span><span class="p">(</span><span class="n">denomiator</span><span class="p">)[</span><span class="n">j</span><span class="p">]:</span> <span class="k">if</span> <span class="nb">int</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">denomiator</span><span class="p">)[(</span><span class="n">j</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="p">])</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">continue</span> <span class="c"># devision through 0 is bad</span> <span class="n">canceled</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">numerator</span><span class="p">)[(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="p">])</span> <span class="o">/</span> \ <span class="nb">int</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">denomiator</span><span class="p">)[(</span><span class="n">j</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="p">])</span> <span class="n">divided</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="n">numerator</span><span class="p">)</span> <span class="o">/</span> <span class="n">denomiator</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">canceled</span><span class="o">-</span><span class="n">divided</span><span class="p">)</span> <span class="o">&lt;</span> <span class="mf">0.0001</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%i</span><span class="s">/</span><span class="si">%i</span><span class="s"> = </span><span class="si">%s</span><span class="s">/</span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">numerator</span><span class="p">,</span> \ <span class="n">denomiator</span><span class="p">,</span> <span class="nb">str</span><span class="p">(</span><span class="n">numerator</span><span class="p">)[(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="p">],</span>\ <span class="nb">str</span><span class="p">(</span><span class="n">denomiator</span><span class="p">)[(</span><span class="n">j</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">%</span><span class="mi">2</span><span class="p">]))</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">10</span><span class="p">,</span> <span class="mi">100</span><span class="p">):</span> <span class="k">if</span> <span class="n">i</span> <span class="o">%</span> <span class="mi">10</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="c"># those are not interesting</span> <span class="k">continue</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="mi">100</span><span class="p">):</span> <span class="n">isCuriousFraction</span><span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">)</span></code></pre></div> <h2>Solving it without programming</h2> <p>You can also solve this without programming at all: See <a href="http://projecteuler.net/thread=33;page=8#86864">post</a>.</p> Project Euler: Problem 32 //martin-thoma.com/project-euler-problem-32/ Tue, 13 Nov 2012 11:52:12 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/project-euler-problem-32 <p>The task in Problem 32 of Project Euler is:</p> <blockquote>We shall say that an `$n$`-digit number is pandigital if it makes use of all the digits 1 to n exactly once; for example, the 5-digit number, 15234, is 1 through 5 pandigital. The product 7254 is unusual, as the identity, `$39 \cdot 186 = 7254$`, containing multiplicand, multiplier, and product is 1 through 9 pandigital. Find the sum of all products whose multiplicand/multiplier/product identity can be written as a 1 through 9 pandigital. HINT: Some products can be obtained in more than one way so be sure to only include it once in your sum.</blockquote> <h2>How to solve it</h2> <p>We have to get a check, if a number is pandigital. It could look like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">isPandigitalString</span><span class="p">(</span><span class="n">string</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Check if string contains a pandigital number. &quot;&quot;&quot;</span> <span class="n">digits</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">string</span><span class="p">)</span> <span class="k">if</span> <span class="n">digits</span> <span class="o">&gt;=</span> <span class="mi">10</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="n">digits</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="nb">str</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">string</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span></code></pre></div> <p>We also need a check if a product of two numbers is 9-pandigital:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">gives9PandigitalProduct</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">):</span> <span class="n">numbers</span> <span class="o">=</span> <span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="o">*</span><span class="n">b</span><span class="p">)</span> <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">numbers</span><span class="p">)</span> <span class="o">!=</span> <span class="mi">9</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="n">isPandigitalString</span><span class="p">(</span><span class="n">numbers</span><span class="p">)</span></code></pre></div> <p>Now you need to figure out how to go through all possible combinations:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">products</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">a</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">100000</span><span class="p">):</span> <span class="k">for</span> <span class="n">b</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="mi">100000</span><span class="p">):</span> <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="o">*</span><span class="n">b</span><span class="p">)</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">b</span><span class="p">))</span> <span class="o">&gt;</span> <span class="mi">9</span><span class="p">:</span> <span class="k">break</span> <span class="k">if</span> <span class="n">gives9PandigitalProduct</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">):</span> <span class="n">products</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">a</span><span class="o">*</span><span class="n">b</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%i</span><span class="s"> x </span><span class="si">%i</span><span class="s"> = </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">,</span> <span class="n">a</span><span class="o">*</span><span class="n">b</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="nb">sum</span><span class="p">(</span><span class="nb">set</span><span class="p">(</span><span class="n">products</span><span class="p">)))</span></code></pre></div> <h2>One-liner</h2> <p>This is from Thaddeus Abiye from Ethiopia:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">print</span> <span class="nb">sum</span><span class="p">(</span><span class="nb">set</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span><span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">[</span><span class="mi">0</span><span class="p">:</span><span class="mi">4</span><span class="p">]),</span><span class="nb">filter</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span><span class="nb">sorted</span><span class="p">([</span><span class="n">i</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="n">x</span><span class="p">])</span><span class="o">==</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">10</span><span class="p">)),[</span><span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="o">*</span><span class="n">b</span><span class="p">)</span><span class="o">+</span><span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="p">)</span><span class="o">+</span><span class="nb">str</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="k">for</span> <span class="n">a</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">2000</span><span class="p">)</span> <span class="k">for</span> <span class="n">b</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">100</span><span class="p">)]))))</span></code></pre></div> <p>It needs one line and 173 characters, but I think it’s hard to read.</p> <h2>Data about my solution</h2> <ul> <li>It worked in less than a second.</li> <li>28 LOC (including whitespaces and comments)</li> <li>719 characters for this solution (including whitespace and comments)</li> </ul> Beweise aus der booleschen Algebra //martin-thoma.com/beweise-aus-der-booleschen-algebra/ Thu, 08 Nov 2012 13:18:09 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/beweise-aus-der-booleschen-algebra <h2 id="definition">Definition</h2> <p>Edward Vermilye Huntington hat eine sehr kompakte Definition boolescher Algebren erarbeitet:</p> <p>Sei <code>$B$</code> eine Menge und <code>$\sqcap: B \times B \rightarrow B$</code> sowie <code>$\sqcup: B \times B \rightarrow B$</code> Verknüfungen auf B.</p> <p>Weiter gelte:</p> <p><strong>H1: Kommutativgesetze</strong></p> <ul style="list-style-type:none;"> <li>`$\forall a,b \in B: a \sqcap b = b \sqcap a$`</li> <li>`$\forall a,b \in B: a \sqcup b = b \sqcup a$`</li> </ul> <p><strong>H2: Distributivgesetze</strong></p> <ul style="list-style-type:none;"> <li>`$\forall a,b,c \in B: a \sqcap (b \sqcup c) = (a \sqcap b) \sqcup (a \sqcap c)$`</li> <li>`$\forall a,b,c \in B: a \sqcup (b \sqcap c) = (a \sqcup b) \sqcup (a \sqcap c)$`</li> </ul> <p><strong>H3: Neutrale Elemente</strong></p> <ul style="list-style-type:none;"> <li>`$\exists e \in B \forall a \in B: a \sqcap e = a$` (e wird Einselement genannt)</li> <li>`$\exists n \in B \forall a \in B: a \sqcup n = a$` (n wird Nullelement genannt)</li> </ul> <p><strong>H4: Komplementäre Elemente</strong></p> <ul style="list-style-type:none;"> <li>`$\forall a \in B: \exists \bar a: a \sqcap \bar a = n \land a \sqcup \bar a = e$`</li> </ul> <p>Dann wird <code>$(B, \sqcap, \sqcup)$</code> eine boolesche Algebra gennant.</p> <h2 id="folgerungen">Folgerungen</h2> <p>Sei im folgendem immer <code>$\mathcal{B} = (B, \sqcap, \sqcup)$</code> eine boolesche Algebra mit dem Einselement „1“ und dem Nullelement „0“.</p> <h3 id="eindeutigkeit-des-nullelements">Eindeutigkeit des Nullelements</h3> <p><u>Behauptung:</u> Es exisitiert genau ein Nullelement für <code>$\mathcal{B}$</code>.<br /> <u>Beweis:</u> direkt</p> <p>Die Existenz von mindestens einem Nullelement wird durch H3 garantiert.</p> <p>Seien <code>$n_1, n_2$</code> Nullelemente auf <code>$\mathcal{B}$</code>. Dann gilt:</p> <p><code>$\begin{align} &amp; \forall a \in B: a \sqcup n_1 \stackrel{H3}{=} a\\ \Rightarrow &amp; n_2 \sqcup n_1 = n_2\\ \stackrel{H3}{\Rightarrow} &amp; n_1 = n_2 \blacksquare \end{align} $</code></p> <h3 id="eindeutigkeit-des-einselements">Eindeutigkeit des Einselements</h3> <p><u>Behauptung:</u> Es exisitiert genau ein Einselement für <code>$\mathcal{B}$</code>.<br /> <u>Beweis:</u> direkt</p> <p>Die Existenz von mindestens einem Einselement wird durch H3 garantiert.</p> <p>Seien <code>$e_1, e_2$</code> Einselemente auf <code>$\mathcal{B}$</code>. Dann gilt:</p> <p><code>$\begin{align} &amp; \forall a \in B: a \sqcap e_1 \stackrel{H3}{=} a\\ \Rightarrow &amp; e_2 \sqcup e_1 = e_2\\ \stackrel{H3}{\Rightarrow} &amp; e_1 = e_2 \blacksquare \end{align}$</code></p> <h3 id="eindeutigkeit-der-komplementaumlren-elemente">Eindeutigkeit der komplementären Elemente</h3> <p><u>Behauptung:</u> Die komplementären Elemente bzgl. <code>$\sqcup$</code> sind eindeutig<br /> <u>Beweis:</u> direkt<br /> Sei <code>$a \in B$</code> beliebig und es gelte:<br /> <code>$a \sqcup \bar a_1 = 0$</code> und <code>$a \sqcup \bar a_2 = 0$</code> sowie<br /> <code>$a \sqcap \bar a_1 = 1$</code> und <code>$a \sqcap \bar a_2 = 1$</code></p> <p>Schritt 1<br /> Es gilt:</p> <p><code>$\begin{align} \bar a_1 \sqcap (a \sqcup \bar a_2) &amp;\stackrel{H2}{=} (\bar a_1 \sqcap a) \sqcup (\bar a_1 \sqcap \bar a_2)\\ \Leftrightarrow \bar a_1 \sqcap 1 &amp;= 0 \sqcup (\bar a_1 \sqcap \bar a_2)\\ \Leftrightarrow \bar a_1 &amp;= \bar a_1 \sqcap \bar a_2 \end{align}$</code></p> <p>Schritt 2<br /> Außerdem gilt:</p> <p><code>$\begin{align} \bar a_2 \sqcap (a \sqcup \bar a_1) &amp;\stackrel{H2}{=} (\bar a_2 \sqcap a) \sqcup (\bar a_2 \sqcap \bar a_1)\\ \Leftrightarrow \bar a_2 \sqcap 1 &amp;= 0 \sqcup (\bar a_2 \sqcap \bar a_1)\\ \Leftrightarrow \bar a_2 &amp;= (\bar a_2 \sqcap \bar a_1) \stackrel{H1}{=} \bar a_1 \sqcap \bar a_2 \end{align}$</code></p> <p>Aus den Ergebnissen von Schritt 1 und Schritt 2 folgt: <code>$\bar a_1 = \bar a_2$</code>.</p> <p>Das bedeutet, zu jedem <code>$a \in B$</code> existiert genau ein Komplement. <code>$\blacksquare$</code></p> <h3 id="nullelement-ungleich-einselement">Nullelement ungleich Einselement</h3> <p><u>Behauptung:</u> <code>$0 \neq 1$</code><br /> <u>Beweis:</u><br /> Wegen (H3) und (H4) gilt:</p> <ul> <li>`$\exists 1 \in B \forall a \in B: a \sqcap 1 \stackrel{H1}{=} 1 \sqcap a = a$`</li> <li>`$\exists 0 \in B \forall a \in B: a \sqcup 0 \stackrel{H1}{=} 0 \sqcup a = a$`</li> <li>`$\forall a \in B: \exists \bar a \in B: a \sqcap \bar a \stackrel{H1}{=} 0$`</li> <li>`$\forall a \in B: \exists \bar a \in B: a \sqcup \bar a \stackrel{H1}{=} 1$`</li> </ul> <p>Annahme: 1 = 0<br /> <code>$\Rightarrow \forall a \in B: \exists \bar a \in B = a \sqcap \bar a = a \sqcup \bar a = 0 = 1$</code></p> <p>Hmmm … irgendwie konnte man <code>$(0 = 1) \Rightarrow (\sqcap = \sqcup)$</code> zeigen … aber wie genau?</p> <h3 id="extremalgesetze">Extremalgesetze</h3> <p><code>$\forall a \in B: 1 \sqcup a = 1$</code> <code>$\forall a \in B: 0 \sqcap a = 0$</code></p> <p>Wie beweist man das?</p> <h3 id="absorptionsgesetz">Absorptionsgesetz</h3> <h4 id="version-1">Version 1</h4> <p><u>Voraussetzungen:</u> Sei <code>$\mathcal{B} = (B, \sqcap, \sqcup)$</code> eine boolesche Algebra.<br /> <u>Behauptung:</u> <code>$\forall a, b \in B: a \sqcup (a \sqcap b) = a$</code><br /> <u>Beweis:</u> direkt</p> <p><code>$a \sqcup (a \sqcap b) \stackrel{H3}{=} (a \sqcap 1) \sqcup (a \sqcap b) \stackrel{H3}{=} a \sqcap (1 \sqcup b) \stackrel{\text{Extremalgesetze}}{=} a \sqcap 1 \stackrel{H3}{=} a$</code></p> <h4 id="version-2">Version 2</h4> <p><u>Voraussetzungen:</u> Sei <code>$\mathcal{B} = (B, \sqcap, \sqcup)$</code> eine boolesche Algebra.<br /> <u>Behauptung:</u> <code>$\forall a, b \in B: a \sqcap (a \sqcup b) = a$</code><br /> <u>Beweis:</u> Duale Aussage zu Version 1<br /></p> <h4 id="version-3">Version 3</h4> <p><u>Voraussetzungen:</u> Sei <code>$\mathcal{B} = (B, \sqcap, \sqcup)$</code> eine boolesche Algebra.<br /> <u>Behauptung:</u> <code>$\forall a, b \in B: a \sqcup (\bar a \sqcap b) \stackrel{H2}{=} a \sqcup b$</code><br /> <u>Beweis:</u> direkt<br /> <code>$a \sqcup (\bar a \sqcap b) \stackrel{H2}{=} (a \sqcup \bar a) \sqcap (a \sqcup b) \stackrel{H4}{=} 1 \sqcap (a \sqcup b) \stackrel{H3}{=} a \sqcup b \blacksquare$</code></p> <h2 id="krper">Körper</h2> <p>Ist jede Boolesche Algebra ein Körper?</p> <p>Ein Körper ist eine Menge <code>$V$</code> mit zwei Verknüpfungen <code>$\oplus, \otimes$</code>: <code>$(V, \oplus, \otimes)$</code>, für den gilt:</p> <ul> <li>`$(K, \oplus)$` ist abelsche Gruppe mit neutralem Element 0</li> <li>`$(K \setminus \{0\}, \otimes)$` ist abelsche Gruppe mit neutralem Element 1</li> <li>Es gelten die Distributivgesetze: <ul> <li>`$\forall a, b, c \in V: a\cdot (b+c) = a\cdot b+a\cdot c$`</li> <li>`$\forall a, b, c \in V: (a+b)\cdot c= a\cdot c+b\cdot c$`</li> </ul> </li> </ul> <p>Es scheint relativ offensichtlich, dass jede boolesche Algebra ein Körper ist. Allerdings muss man aufpassen. Für die neutrale Elemente eines Körpers <code>$K = (V, \oplus, \otimes)$</code> muss gelten:</p> <ul> <li>`$\forall a: 0 \oplus a = a$`</li> <li>`$\forall a: 1 \otimes a = a$`</li> </ul> <p>Für eine boolesche Algebra <code>$\mathcal{B} = (B, \sqcap, \sqcup)$</code> muss gelten (H3):</p> <ul> <li>`$\exists 1 \in B \forall a \in B: a \sqcap 1 = a$`</li> <li>`$\exists 0 \in B \forall a \in B: a \sqcup 0 = a$`</li> </ul> <p>Für die Inversen von <code>$K$</code> muss gelten:</p> <ul> <li>`$\forall a \exists \bar a: a \oplus \bar a = 0$`</li> <li>`$\forall a \exists \bar a: a \otimes \bar a = 1$`</li> </ul> <p>Für die Komplemente von <code>$\mathcal{B}$</code> muss gelten:</p> <ul> <li>`$\forall a \in B: \exists \bar a: a \sqcap \bar a = 0$`</li> <li>`$\forall a \in B: \exists \bar a: a \sqcup \bar a = 1$`</li> </ul> <p>Das Komplement eines Elements verknüfpft mit <code>$\sqcap$</code> ergibt also das neutrale Element von <code>$\sqcup$</code>!</p> <p>Offensichtlich ist, dass die Schaltalgebra mit den Operatoren XOR und AND, also <code>$(\{0,1\}, XOR, AND)$</code> ein Körper ist, da Sie offensichtlich isomorph zu <code>$\mathbb{Z}/2\mathbb{Z}$</code> ist.</p> <p><u>Behauptung:</u> Alle booleschen Algebren mit drei oder mehr Elementen sind keine Körper<br /> <u>Beweis:</u> (<a href="http://de.wikipedia.org/wiki/Diskussion:Darstellungssatz_f%C3%BCr_Boolesche_Algebren#Beziehung zu K&ouml;rpern">danke an Chricho</a>) Sei <code>$\mathcal{B} = (B, \sqcap, \sqcup)$</code> mit <code>$|B| \geq 3$</code>. Sei <code>$a \in B$</code> mit <code>$0 \neq a \neq 1$</code>. <br /> Es gilt:<br /> <code>$\forall b \in B: a \land b \leq a \lneq 1 \Rightarrow a$</code> hat kein Inverses <code>$\Rightarrow \mathcal{B}$</code> ist kein Körper <code>$\blacksquare$</code></p> <h2 id="boolesche-algebren-und-die-schaltalgebra">Boolesche Algebren und die Schaltalgebra</h2> <p>Die wohl bekannteste boolesche Algebra ist die Schaltalgebra: <code>$(\{0,1\}, \lor, \land, 0, 1)$</code></p> <p>Allerdings ist nicht jede Boolesche Algebra eine Schaltalgebra!</p> <h2 id="quellen">Quellen</h2> <ul> <li>Skript &bdquo;Technische Informatik - Digitaltechnik und Entwurfsverfahren&ldquo; von Dr.-Ing. Tamim Asfour. S.33 - 37</li> <li><a href="http://ti.ira.uka.de/TI-1/Vorlesung/Vorlesung.php">Folien</a> von Dr.-Ing. Tamim Asfour</li> <li><a href="http://youtu.be/2G-MQPKylPA?t=38m12s">Vorlesung</a> von Dr.-Ing. Tamim Asfour</li> </ul> Definitionen aus Digitaltechnik //martin-thoma.com/definitionen-aus-digitaltechnik/ Wed, 07 Nov 2012 13:33:53 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/definitionen-aus-digitaltechnik <div class="info">Dieser Blogpost ist vor allem f&uuml;r H&ouml;rer von Prof. Dr. Asfour im WS 2012 / 2013 interessant. Ich h&ouml;re momentan die Vorlesung bei ihm. Deshalb sind die Inhalte teilweise identisch oder zumindest sehr &auml;hnlich.</div> <p>Dieser Blogpost soll nur möglichst gute Definitionen liefern. Ich werde ihn vermutlich bis zum Ende des Semesters immer wieder erweitern.</p> <h2>Boolesche Algebra</h2> <p><a href="http://de.wikipedia.org/wiki/Konjunktion_(Logik)">Konjunktion</a>: <code>$\land$</code> <a href="http://de.wikipedia.org/wiki/Disjunktion">Disjunktion</a>: <code>$\lor$</code></p> <div class="definition">Sei `$x$` eine Variable. L hei&szlig;t <strong>Literal</strong> `$:\Leftrightarrow L \in \{x, \bar x\}$`.</div> <div class="definition">Seien `$L_1, \dots, L_n$` Literale. `$K(x_1, \dots, x_n)$` hei&szlig;t ein <strong>Produktterm</strong> `$:\Leftrightarrow K(x_1, \dots, x_n) = \bigwedge_{i=1}^n L_i$` oder `$K = 1$` oder `$K=0$`.</div> <p>Jeder Produktterm <code>$K(x_1, \dots, x_n)$</code> kann so dargestellt werden, dass eine Variable <code>$x$</code> in höchstens einem Literal vorkommt.</p> <div class="definition">Sei `$K(x_1, \dots, x_n)$` ein Produktterm und `$y(x_1, \dots x_n)$` eine boolesche Funktion. `$K$` hei&szlig;t <strong>Implikant</strong> von `$y :\Leftrightarrow (K \Rightarrow y)$`</div> <div class="definition">Sei `$K(x_1, \dots, x_n)$` ein Implikant der boolesche Funktion `$y(x_1, \dots x_n)$`. `$K$` hei&szlig;t <strong>Minterm</strong> von `$y :\Leftrightarrow$` F&uuml;r jede Variable `$x_i$` in `$y$` kommt genau ein mal in `$K$` als Literal vor.</div> <div class="definition">Sei `$y(x_1, \dots x_n)$` eine boolesche Funktion und `$x$` ein boolescher Ausdruck, der `$y$` entspricht. `$x$` hei&szlig;t <strong>disjunktive Normalform</strong> (DNF) von `$y :\Leftrightarrow$` `$x=\bigvee_{i=0}^k K_i, \; k \leq 2^n - 1:\quad K_i \neq K_j \Leftrightarrow i \neq j$`</div> <div class="definition">Sei `$D(x_1, \dots, x_m)$` eine Disjunktion von Literalen `$\bigvee_{i=1}^m L_i$` oder die Konstante &bdquo;0&ldquo; oder die Konstante &bdquo;1&ldquo;. Sei weiter `$y(x_1, \dots x_n)$` eine boolesche Funktion. `$D$` hei&szlig;t <strong>Implikat</strong> von `$y :\Leftrightarrow \bar D \Rightarrow \bar y$`</div> <p>Summenterm ist ein Synonym zu Implikat.</p> <div class="definition">Sei `$y(x_1, \dots x_n)$` eine boolesche Funktion und `$D$` ein Implikat von `$y$`. `$D$` hei&szlig;t <strong>Maxterm</strong> von `$y :\Leftrightarrow$` Ein Literal jeder Variable `$x_i$` der Funktion `$y$` kommt in `$D$` genau einmal vor.</div> <p>Beispiele:</p> <table class="wikitable"> <tr> <th>&nbsp;</th> <th>Minterm</th> <th>Maxterm</th> </tr> <tr> <td>0</td> <td>`$\bar a \bar b \bar c$`</td> <td>`$a \lor b \lor c$`</td> </tr> <tr> <td>1</td> <td>`$a \bar b \bar c$`</td> <td>`$\bar a \lor b \lor c$`</td> </tr> <tr> <td>2</td> <td>`$\bar a b \bar c$`</td> <td>`$a \lor \bar b \lor c$`</td> </tr> <tr> <td>3</td> <td>`$a b \bar c$`</td> <td>`$\bar a \lor \bar b \lor c$`</td> </tr> <tr> <td>4</td> <td>`$\bar a \bar b c$`</td> <td>`$a \lor b \lor \bar c$`</td> </tr> <tr> <td>5</td> <td>`$a \bar b c$`</td> <td>`$\bar a \lor b \lor \bar c$`</td> </tr> <tr> <td>6</td> <td>`$\bar a b c$`</td> <td>`$a \lor \bar b \lor \bar c$`</td> </tr> <tr> <td>0</td> <td>`$a b c$`</td> <td>`$\bar a \lor \bar b \lor \bar c$`</td> </tr> </table> <div class="definition">Ein boolescher Ausdruck der Form `$\bigwedge_i \bigvee_j (\neg)x_{ij}$` wird <strong>konjunktive Normalform</strong> (KNF) genannt.</div> What is the best programming language? //martin-thoma.com/what-is-the-best-programming-language/ Sat, 03 Nov 2012 11:48:36 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-is-the-best-programming-language <p>There is no such thing as a best programming language. Sorry about that, I’ve just thought it would be a catchy title. I would rather choose my tools after I know the problem I have to solve.</p> <p>Some programming languages are very good at some tasks. I don’t know any that is very good at every task.</p> <p>This comic illustrates what I mean:</p> <div style="width: 592px" class="wp-caption alignnone"><a href="../images/2012/07/testing_cartoon.jpg"><img src="../images/2012/07/testing_cartoon.jpg" alt="A fair test - comic - illustration - cartoon - caricature" width="" height="" class="size-full wp-image-32731 " /></a><p class="wp-caption-text">A fair test</p></div> <h2>Bash</h2> <p>The bash is great for tiny tasks where other programs are involved.</p> <h3>Example</h3> <p>Resizing all jpg-images in a given folder to a maximum resolution of 1600x1600 while maintaining the aspect ratio:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="k">for</span> i in *.JPG<span class="p">;</span><span class="k">do</span> convert <span class="s2">&quot;`$i&quot;</span> -resize 1600x1600 <span class="s2">&quot;$`{i%.JPG}-resized.jpg&quot;</span><span class="p">;</span> <span class="k">done</span></code></pre></div> <p>See <a href="../converting-files-with-linux/">Converting Files with Linux</a> for more examples.</p> <h2>Python</h2> <p>Python does a incredibly well job for small problems. I don’t have experience with big projects, but some have been done using Python (see list below). Python is dynamically typed, offers a lot of functions out of the box and is easy to learn and understand. You might argue that Python is executable Pseudocode as it is so easy to read. Additionally, it offers a very neat library for math functions with <a href="http://docs.scipy.org/doc/">NumPy</a>.</p> <p>Examples of Python-Code in applications include:</p> <ul> <li><a href="http://security.stackexchange.com/a/2897">PDF malware analysis</a></li> <li><a href="http://en.wikipedia.org/wiki/BitTorrent_(software)">BitTorrent</a></li> <li>My <a href="../python-one-liners-for-project-euler/">ProjectEuler Snippets</a> ☺</li> <li>Scripting within an application: <ul> <li><a href="http://en.wikipedia.org/wiki/GIMP">GIMP</a></li> <li><a href="http://en.wikipedia.org/wiki/Blender_(software)">Blender</a></li> </ul> </li> <li>Websites and Services: <ul> <li><a href="http://en.wikipedia.org/wiki/GNU_Mailman">GNU Mailman</a></li> <li><a href="http://en.wikipedia.org/wiki/Reddit">Reddit</a></li> <li><a href="http://en.wikipedia.org/wiki/Trac">Trac</a></li> </ul> </li> </ul> <h2>Java</h2> <p>Java is used in the economy for <strong>simple, but huge tasks</strong>. It is <a href="http://en.wikipedia.org/wiki/Type_system#Static_typing">static</a> and <a href="http://en.wikipedia.org/wiki/Type_system#Strong_and_weak_typing">strong</a> typed, has some widely used <a href="http://www.oracle.com/technetwork/java/codeconvtoc-136057.html">coding convetions</a>, is easy to learn and has a big library.</p> <p>Here are some examples for programs written in Java:</p> <ul> <li>Mars Rovers (<a href="http://java.sys-con.com/node/39220">source</a>)</li> <li>BitTorrent client <a href="http://en.wikipedia.org/wiki/Vuze">Vuze</a></li> <li>Sites that have URLs like "*.do", "*.jsp" and "...servlet..." are most likely written in Java.</li> <li>Games: <ul> <li><a href="http://en.wikipedia.org/wiki/FreeCol">FreeCol</a></li> <li><a href="http://en.wikipedia.org/wiki/Minecraft">Minecraft</a></li> </ul> </li> </ul> <h2>C++</h2> <p>C++ is easy to write and blazing-fast. See <a href="../matrix-multiplication-python-java-cpp/">Performance of Matrix multiplication in Python, Java and C++</a>.</p> <p>Some projects done in C++ are:</p> <ul> <li>NASA flight software: 300k LOC (<a href="http://trs-new.jpl.nasa.gov/dspace/bitstream/2014/37499/1/05-0539.pdf">source</a>)</li> <li><a href="http://en.wikipedia.org/wiki/Google_Chrome">Chrome</a>, <a href="http://en.wikipedia.org/wiki/Firefox">Firefox</a></li> <li>Games: <ul> <li><a href="http://en.wikipedia.org/wiki/Cube_2:_Sauerbraten">Cube 2: Sauerbraten</a></li> <li><a href="http://en.wikipedia.org/wiki/UFO:_Alien_Invasion">UFO: Alien Invasion</a></li> <li><a href="http://en.wikipedia.org/wiki/The_Battle_for_Wesnoth">The Battle for Wesnoth</a></li> <li><a href="http://www.openclonk.org/">OpenClonk</a> (<a href="http://hg.openclonk.org/openclonk/">Repository</a>)</li> <li><a href="http://www.openlierox.net/">OpenLierox</a> (<a href="https://github.com/albertz/openlierox">Repository</a>)</li> <li><a href="http://secretmaryo.org/">Secret Maryo Chronicles</a> (<a href="https://github.com/FluXy/SMC">Repository</a>)</li> </ul> </li> </ul> <h2>C</h2> <p>See <a href="http://programmers.stackexchange.com/questions/103897/is-the-c-programming-language-still-used">Is C still used?</a> and a <a href="http://thread.gmane.org/gmane.comp.version-control.git/57643/focus=57918">comment from Linus Torvalds</a>.</p> <p>Programs done with C:</p> <ul> <li><a href="http://jonls.dk/freeserf/">Freeserf</a> (<a href="https://github.com/jonls/freeserf">Repository</a>)</li> </ul> <h2>See also</h2> <ul> <li><a href="http://readwrite.com/2012/06/05/5-ways-to-tell-which-programming-lanugages-are-most-popular">5 Ways to Tell Which Programming Languages are Most Popular</a></li> <li><a href="http://osgameclones.com/">OpenGameClones</a></li> </ul> <h2>Matlab</h2> <p><a href="http://stackoverflow.com/q/179904/562769">What is MATLAB good for? Why is it so used by universities? When is it better than Python?</a></p> <p>Do you know some more programs that are famous and should be in these lists? Preferably with an open repository?</p> Error correcting Codes //martin-thoma.com/error-correcting-codes/ Fri, 26 Oct 2012 22:29:51 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/error-correcting-codes <div class="info">This blogpost is strongly related to <a href="http://page.math.tu-berlin.de/~felsner/DMSWe/Aufgaben/codes.pdf">this germand PDF</a> of a pupils' competition in which I have participated in 2008.</div> <p>Today, we have a lot of data that is stored or transferred in a binary way. Once in a while an error occurs and single bits get switched from 0 to 1 or the other way around. <a href="http://en.wikipedia.org/wiki/Coding_theory">Coding theory</a> tries to find algorithms with which you can <strong>detect</strong> and <strong>correct</strong> errors.</p> <h2>Introduction</h2> <p>To keep it simple, we make a small example. We have <code>$2^3 = 8$</code> valid messages:</p> <p>Message A: (0, 0, 0) Message B: (0, 0, 1) Message C: (0, 1, 0) Message D: (0, 1, 1) Message E: (1, 0, 0) Message F: (1, 0, 1) Message G: (1, 1, 0) Message H: (1, 1, 1)</p> <p>I will call the set <code>$c_1 := \{A, B, C, D, E, F, G, H\}$</code> of those messages a <strong>code</strong>.</p> <p>Now Alice wants to send message A to Bob. If one error occurs, Bob receives either message B, message C or message E. As all of those are valid messages, he might not notice that an error occurred (and even more not be able to correct the error).</p> <p>How could Alice and Bob solve this problem?</p> <h2>Redundancy</h2> <p>Well, a simple solution would be to send the message twice. Or, almost the same, sending once a message with redundant information. So the new messages are:</p> <p>Message A’: (0, 0, 0, 0, 0, 0) Message B’: (0, 0, 1, 0, 0, 1) Message C’: (0, 1, 0, 0, 1, 0) Message D’: (0, 1, 1, 0, 1, 1) Message E’: (1, 0, 0, 1, 0, 0) Message F’: (1, 0, 1, 1, 0, 1) Message G’: (1, 1, 0, 1, 1, 0) Message H’: (1, 1, 1, 1, 1, 1)</p> <p><code>$c_2 := \{A', B', C', D', E', F', G', H'\}$</code></p> <p>If Bob gets a message with only one error, he can detect it. But he still isn’t able to correct it: Alice send Message A and an error occurred at the first (most significant) bit. Bob can see that this is not a valid message, but if he thinks that only one error occurred, it is equally likely that Alice sent message A or message E.</p> <p>Can we do better?</p> <h2>Hamming distance</h2> <p>A useful tool is the so called “<a href="http://en.wikipedia.org/wiki/Hamming_distance">Hamming distance</a>”.</p> <p>The set of all 0/1 tuples of the length <code>$n$</code> is called <code>$\mathcal{F}_n$</code>.</p> <p>Examples: <code>$\begin{align} \{A, B, C, D, E, F, G, H\} &amp;= \mathcal{F}_3\\ \{A', B', C', D', E', F', G', H'\} &amp;\subsetneq \mathcal{F}_8 \end{align}$</code></p> <p><code>$A[i]$</code> is the <code>$i$</code>-th bit of a message <code>$A$</code> with <code>$i \in \{0, \dots, (n-1)\}$</code></p> <p><code>$\oplus : \{0,1\} \times \{0,1\} \rightarrow \{0,1\}$</code> defined as <code>$\oplus(a, b) := \begin{cases} 0 &amp; \text{, if } a = b\\ 1 &amp; \text{, if } a \neq b\\ \end{cases}$</code>. (<code>$\oplus$</code> is XOR).</p> <p>The Hamming distance is a function <code>$h: \mathcal{F}_n \times \mathcal{F}_n \rightarrow \mathbb{N}_0$</code> defined as: <code>$\displaystyle h(A, B) := \sum_{i=0}A[i] \oplus B[i]$</code></p> <p>The minimum Hamming distance is defined as: <code>$\displaystyle h_\text{min}(\text{code}) = \min(\{h(A, B) | A, B \in \text{code}, A \neq B\})$</code></p> <h3>First example</h3> <table class="wikitable"> <tr> <th>&nbsp;</th> <th>A</th> <th>B</th> <th>C</th> <th>D</th> <th>E</th> <th>F</th> <th>G</th> <th>H</th> </tr> <tr> <th>A</th> <td>0</td> <td>1</td> <td>1</td> <td>2</td> <td>1</td> <td>2</td> <td>2</td> <td>3</td> </tr> <tr> <th>B</th> <td>1</td> <td>0</td> <td>2</td> <td>1</td> <td>2</td> <td>1</td> <td>3</td> <td>2</td> </tr> <tr> <th>C</th> <td>1</td> <td>2</td> <td>0</td> <td>1</td> <td>2</td> <td>3</td> <td>2</td> <td>2</td> </tr> <tr> <th>D</th> <td>2</td> <td>1</td> <td>1</td> <td>0</td> <td>3</td> <td>2</td> <td>2</td> <td>1</td> </tr> <tr> <th>E</th> <td>1</td> <td>2</td> <td>2</td> <td>3</td> <td>0</td> <td>1</td> <td>1</td> <td>2</td> </tr> <tr> <th>F</th> <td>2</td> <td>1</td> <td>3</td> <td>2</td> <td>1</td> <td>0</td> <td>2</td> <td>1</td> </tr> <tr> <th>G</th> <td>2</td> <td>3</td> <td>1</td> <td>2</td> <td>1</td> <td>1</td> <td>0</td> <td>1</td> </tr> <tr> <th>H</th> <td>3</td> <td>2</td> <td>2</td> <td>1</td> <td>2</td> <td>1</td> <td>1</td> <td>0</td> </tr> </table> <p><code>$h_\text{min}(c_1) = 1$</code></p> <h3>Second example</h3> <table class="wikitable"> <tr> <th>&nbsp;</th> <th>A'</th> <th>B'</th> <th>C'</th> <th>D'</th> <th>E'</th> <th>F'</th> <th>G'</th> <th>H'</th> </tr> <tr> <th>A'</th> <td>0</td> <td>2</td> <td>2</td> <td>4</td> <td>2</td> <td>4</td> <td>4</td> <td>6</td> </tr> <tr> <th>B'</th> <td>2</td> <td>0</td> <td>4</td> <td>2</td> <td>4</td> <td>2</td> <td>6</td> <td>4</td> </tr> <tr> <th>C'</th> <td>2</td> <td>4</td> <td>0</td> <td>2</td> <td>4</td> <td>6</td> <td>2</td> <td>4</td> </tr> <tr> <th>D</th> <td>4</td> <td>2</td> <td>2</td> <td>0</td> <td>6</td> <td>4</td> <td>4</td> <td>2</td> </tr> <tr> <th>E'</th> <td>2</td> <td>4</td> <td>4</td> <td>6</td> <td>0</td> <td>2</td> <td>2</td> <td>4</td> </tr> <tr> <th>F'</th> <td>4</td> <td>2</td> <td>6</td> <td>4</td> <td>2</td> <td>0</td> <td>4</td> <td>2</td> </tr> <tr> <th>G'</th> <td>4</td> <td>6</td> <td>2</td> <td>4</td> <td>2</td> <td>4</td> <td>0</td> <td>2</td> </tr> <tr> <th>H'</th> <td>6</td> <td>4</td> <td>4</td> <td>2</td> <td>4</td> <td>2</td> <td>2</td> <td>0</td> </tr> </table> <p><code>$h_\text{min}(c_2) = 2$</code></p> <h2>Detection and correction of errors</h2> <p>If I didn’t make a typo, those tables should be symmetrical (as XOR is symmetrical) and the hamming distance of a message to itself is 0.</p> <p>The higher the minimum hamming distance of a code is, the more errors can be detected and corrected. In fact, you can quite easily quantise the relationship:</p> <div class="definition">Let `$c$` be a code with `$h_\text{min}(c) = 2e + 1 \quad e \in \mathbb{N}^+$`. `$2e$` is the maximum number of errors that can be detected and `$e$` is the maximum number of errors that can be corrected.</div> <p>A code with length <code>$n$</code> which has <code>$M$</code> elements and a minimum Hamming distance of <code>$d$</code> is called a <code>$(n, M, d)$</code>-Code.</p> <p>Example: <code>$c_1$</code> is a <code>$(3, 8, 1)$</code> code and <code>$c_2$</code> is a <code>$(6, 8, 2)$</code> code.</p> <p>The task of coding thery is: You’re given a <code>$n$</code> and a <code>$d$</code> and you should find the code words so that M is as high as possible.</p> <h3>Example of a (6, 8, 3)-Code</h3> <p><code>$\begin{align} c_3 = \{&amp;(1,1,1,1,1,1),\\ &amp;(0,0,0,0,1,1),\\ &amp;(0,0,1,1,0,0),\\ &amp;(0,1,0,1,0,1),\\ &amp;(0,1,1,0,1,0),\\ &amp;(1,0,0,1,1,0),\\ &amp;(1,0,1,0,0,1),\\ &amp;(1,1,0,0,0,0)\} \end{align} $</code></p> <h2>Hamming codes</h2> <p><a href="http://en.wikipedia.org/wiki/Hamming_code">Hamming codes</a> are a family of <code>$(2^k - 1, 2^{(2^k -1)-k}, 3), \quad k \geq 2$</code> codes. This means, every hamming code can only correct one error.</p> <p>The idea behind Hamming codes is to save in one bit if the number of a fixed set of positions of the message is even or odd. This is called parity and done with XOR. The parity-bit is saved at the end of the message (or, just another point of view: the positions that are powers of two (1, 2, 4, 8, …) of each message are only parity bits. This are obviously <code>$\lceil \log_2(\text{length of code}) \rceil = \lceil \log(2^k - 1) \rceil = k$</code>).</p> <p>Wikipedia has a really nice image for that:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/10/hamming-code-parity.png"><img src="../images/2012/10/hamming-code-parity.png" alt="Parity-bits and data bits in a Hamming codeword" width="" height="" class="size-full wp-image-47691" /></a><p class="wp-caption-text">Parity-bits and data bits in a Hamming codeword</p></div> <p>Now, how are the parity-bits calculated? Well, think of each messages as a vector in <code>$\{0,1\}^{(2^k - 1) - k}$</code>. Then you define a matrix <code>$G \in \{0,1\}^{2^k - 1} \times \{0,1\}^{(2^k - 1) - k}$</code>. Now you can get the codewords <code>$c$</code> by multiplying the datawords <code>$d$</code> (messages) with <code>$G$</code>: <code>$c = G \cdot d$</code>. This is the reason why Hamming-Codes are called “linear codes”. They can be obtained by a linear function.</p> <p>How do I get the generator-matrix <code>$G$</code>? I don’t know it and my internet searches didn’t reveal any solution. Do you know one?</p> A practical approach to floats //martin-thoma.com/a-practical-approach-to-floats/ Tue, 23 Oct 2012 12:40:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/a-practical-approach-to-floats <p>If you make a computer science degree, you will have to learn how numbers are internally represented. Most of the time, you get explanations like the pictures below:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/10/IEEE_754_single_precision.png"><img src="../images/2012/10/IEEE_754_single_precision.png" alt="IEEE 754 single precision" width="" height="" class="size-full wp-image-47381" /></a><p class="wp-caption-text">IEEE 754 single precision</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/10/float-scheme.png"><img src="../images/2012/10/float-scheme.png" alt="Example of a floating point number" width="" height="" class="size-full wp-image-47361" /></a><p class="wp-caption-text">Example of a floating point number</p></div> <p>You will (have to) learn how <a href="http://en.wikipedia.org/wiki/IEEE_floating_point">IEEE 754 floats</a> are structured on a bit-wise level. But I also like to check if it is correct, what I’ve learned.</p> <p>So this is how you can check it:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdint.h&gt;</span> <span class="cp">#include &lt;stdio.h&gt; </span><span class="c1">// printf</span> <span class="cp">#include &lt;limits.h&gt; </span><span class="c1">// INT_MAX, UINT_MAX, ...</span> <span class="cp">#include &lt;math.h&gt; </span><span class="c1">// needed for NAN</span> <span class="k">union</span> <span class="n">myUnion</span> <span class="p">{</span> <span class="kt">uint32_t</span> <span class="n">i</span><span class="p">;</span> <span class="c1">// unsigned integer 32-bit type (on every machine)</span> <span class="kt">float</span> <span class="n">f</span><span class="p">;</span> <span class="c1">// a type you want to play with</span> <span class="p">};</span> <span class="kt">void</span> <span class="nf">printValue</span><span class="p">(</span><span class="k">union</span> <span class="n">myUnion</span> <span class="n">u</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;uint32_t</span><span class="se">\t</span><span class="s">:</span><span class="se">\t</span><span class="s">%u</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">u</span><span class="p">.</span><span class="n">i</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Bits</span><span class="se">\t\t</span><span class="s">:</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">31</span><span class="p">;</span> <span class="n">i</span> <span class="o">&gt;=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">--</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;%i&quot;</span><span class="p">,</span> <span class="p">(</span><span class="n">u</span><span class="p">.</span><span class="n">i</span> <span class="o">&gt;&gt;</span> <span class="n">i</span><span class="p">)</span> <span class="o">%</span> <span class="mi">2</span><span class="p">);</span> <span class="k">if</span> <span class="p">(</span><span class="n">i</span> <span class="o">!=</span> <span class="mi">0</span> <span class="o">&amp;&amp;</span> <span class="n">i</span> <span class="o">%</span> <span class="mi">4</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;.&quot;</span><span class="p">);</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="n">i</span> <span class="o">==</span> <span class="mi">31</span> <span class="o">||</span> <span class="n">i</span> <span class="o">==</span> <span class="mi">23</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;|&quot;</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\n</span><span class="s">Number</span><span class="se">\t\t</span><span class="s">:</span><span class="se">\t</span><span class="s">%0.10f</span><span class="se">\n\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">u</span><span class="p">.</span><span class="n">f</span><span class="p">);</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">setSign</span><span class="p">(</span><span class="k">union</span> <span class="n">myUnion</span> <span class="o">*</span><span class="n">u</span><span class="p">,</span> <span class="kt">char</span> <span class="n">sign</span><span class="p">)</span> <span class="p">{</span> <span class="n">u</span><span class="o">-&gt;</span><span class="n">i</span> <span class="o">=</span> <span class="p">(</span><span class="n">u</span><span class="o">-&gt;</span><span class="n">i</span> <span class="o">&amp;</span> <span class="p">(</span><span class="mh">0xffffffff</span> <span class="o">-</span> <span class="p">(</span><span class="mi">1</span> <span class="o">&lt;&lt;</span> <span class="mi">31</span><span class="p">)))</span> <span class="o">+</span> <span class="p">(</span><span class="n">sign</span> <span class="o">&lt;&lt;</span> <span class="mi">31</span><span class="p">);</span> <span class="p">}</span> <span class="cm">/**</span> <span class="cm"> * The exponent has 8 bits.</span> <span class="cm"> * When all bits are 0, you switch to denormalized numbers.</span> <span class="cm"> * When all bits are 1, you get either NaN or infinity, depending on</span> <span class="cm"> * your characteristic. If the characteristic is 0, you get infinity.</span> <span class="cm"> * Otherwise NaN.</span> <span class="cm"> */</span> <span class="kt">void</span> <span class="nf">setExponent</span><span class="p">(</span><span class="k">union</span> <span class="n">myUnion</span> <span class="o">*</span><span class="n">u</span><span class="p">,</span> <span class="kt">char</span> <span class="n">exponent</span><span class="p">)</span> <span class="p">{</span> <span class="n">u</span><span class="o">-&gt;</span><span class="n">i</span> <span class="o">=</span> <span class="p">(</span><span class="n">u</span><span class="o">-&gt;</span><span class="n">i</span> <span class="o">&amp;</span> <span class="p">(</span><span class="mh">0xffffffff</span> <span class="o">-</span> <span class="p">(</span><span class="mh">0xff</span> <span class="o">&lt;&lt;</span> <span class="mi">23</span><span class="p">)))</span> <span class="o">+</span> <span class="p">(</span><span class="n">exponent</span> <span class="o">&lt;&lt;</span> <span class="mi">23</span><span class="p">);</span> <span class="p">}</span> <span class="cm">/**</span> <span class="cm"> * The mantissa has 23 bits.</span> <span class="cm"> */</span> <span class="kt">void</span> <span class="nf">setMantissa</span><span class="p">(</span><span class="k">union</span> <span class="n">myUnion</span> <span class="o">*</span><span class="n">u</span><span class="p">,</span> <span class="kt">int</span> <span class="n">mantissa</span><span class="p">)</span> <span class="p">{</span> <span class="n">u</span><span class="o">-&gt;</span><span class="n">i</span> <span class="o">=</span> <span class="p">(</span><span class="n">u</span><span class="o">-&gt;</span><span class="n">i</span> <span class="o">&amp;</span> <span class="p">(</span><span class="mh">0xffffffff</span> <span class="o">-</span> <span class="p">(</span><span class="mh">0xff</span> <span class="o">&lt;&lt;</span> <span class="mi">0</span><span class="p">)))</span> <span class="o">+</span> <span class="p">(</span><span class="n">mantissa</span> <span class="o">&lt;&lt;</span> <span class="mi">0</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="k">union</span> <span class="n">myUnion</span> <span class="n">testVar</span><span class="p">;</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Manual guessing</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="n">testVar</span><span class="p">.</span><span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">setSign</span><span class="p">(</span><span class="o">&amp;</span><span class="n">testVar</span><span class="p">,</span> <span class="mi">1</span><span class="p">);</span> <span class="n">setExponent</span><span class="p">(</span><span class="o">&amp;</span><span class="n">testVar</span><span class="p">,</span> <span class="mh">0x01</span><span class="p">);</span> <span class="n">setMantissa</span><span class="p">(</span><span class="o">&amp;</span><span class="n">testVar</span><span class="p">,</span> <span class="mh">0x00</span><span class="p">);</span> <span class="n">printValue</span><span class="p">(</span><span class="n">testVar</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;What does UINT_MAX evaluate to?</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="n">testVar</span><span class="p">.</span><span class="n">i</span> <span class="o">=</span> <span class="n">UINT_MAX</span><span class="p">;</span> <span class="n">printValue</span><span class="p">(</span><span class="n">testVar</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;What does nan evaluate to?</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="n">testVar</span><span class="p">.</span><span class="n">f</span> <span class="o">=</span> <span class="n">NAN</span><span class="p">;</span> <span class="n">printValue</span><span class="p">(</span><span class="n">testVar</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;The example above and switched first bit on</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="n">testVar</span><span class="p">.</span><span class="n">i</span> <span class="o">=</span> <span class="mh">0xbf200000</span><span class="p">;</span> <span class="n">printValue</span><span class="p">(</span><span class="n">testVar</span><span class="p">);</span> <span class="p">}</span></code></pre></div> <p>I think I have tried all interesting values. Have fun trying it yourself ☺</p> <p>(hmm … I could also try to make a visualization … I will think about this when I have more time)</p> Java Puzzle #14: Integers //martin-thoma.com/java-puzzle-14-integers/ Mon, 22 Oct 2012 12:00:44 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-14-integers <p>What is the output of the following script?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">SomeClass</span> { <span style="color:#088;font-weight:bold">public</span> <span style="color:#088;font-weight:bold">static</span> <span style="color:#339;font-weight:bold">void</span> main(<span style="color:#0a8;font-weight:bold">String</span><span style="color:#339;font-weight:bold">[]</span> args) { <span style="color:#339;font-weight:bold">int</span> x = <span style="color:#00D">2147483647</span>; <span style="color:#777">// 2147483647 == 2**31 - 1</span> <span style="color:#080;font-weight:bold">if</span> (x &lt; <span style="color:#00D">2</span>*x) { <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Everything's ok:</span><span style="color:#710">&quot;</span></span>); } <span style="color:#080;font-weight:bold">else</span> { <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">It's weird:</span><span style="color:#710">&quot;</span></span>); } <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">x = </span><span style="color:#710">&quot;</span></span> + x); <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">2*x = </span><span style="color:#710">&quot;</span></span> + <span style="color:#00D">2</span>*x); } } </pre></div> </div> </div> <p>. . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-text" data-lang="text">It&#39;s weird: x = 2147483647 2*x = -2</code></pre></div> <h2>Explanation</h2> <p><code>2*x</code> is out of Java Integer range, so it comes back at the other end.</p> Programmieren Tutorium //martin-thoma.com/programmieren-tutorium/ Sun, 21 Oct 2012 20:59:33 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/programmieren-tutorium <div class="info">Programmieren ist ein Modul am <a href="http://de.wikipedia.org/wiki/Karlsruher_Institut_f%C3%BCr_Technologie">KIT</a>. Dieser Blogpost richtet sich also vor allem an Studenten des KIT, die im WS 2012/2013 dieses Modul belegen und mein Tutorium besuchen. Er wird regelmäßig aktualisiert.</div> <h2>Vorlesung</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/videoseries?list=PL22ZNLSohCREsVdSWmjbuST0ba64OctHk&amp;hl=en_US" frameborder="0" allowfullscreen=""></iframe> <h2>Daten</h2> <p>Es gibt momentan (Stand: 10.10.2012) 820 Studenten, in der Programmieren-Vorlesung:</p> <ul> <li>530 Informatiker</li> <li>130 Informationswirte</li> <li>60 Wiederholer</li> <li>70 andere Fakultäten</li> <li>20 Schüler-Studenten</li> </ul> <p>(Ich weiß, dass das in der Summe nur 810 Studenten sind. Aber leider hatte ich nur eine mündliche Quelle und kann es deshalb nicht ausbessern.)</p> <h2>Folien</h2> <p>Sind <a href="https://github.com/MartinThoma/prog-ws1213">hier</a> zu finden. Dort sind auch Code-Beispiele aus dem Tutorium.</p> <p>Die <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/presentations/Programmieren-Tutorium">LaTeX-Quelldateien</a> stehen auch zur Verfügung. Wenn ihr diese verwendet, dann verlinkt bitte auf <code>martin-thoma.com/programmieren-tutorium</code>.</p> <p>Die Einverständniserklärung (Disclaimer) könnt ihr <a href="https://github.com/MartinThoma/prog-ws1213/blob/master/Dokumente/2012-10-15_Einverst%C3%A4ndniserklaerung.pdf?raw=true">hier</a> herunterladen.</p> <h2>Tutorials</h2> <p>Folgendes textbasierte Tutorial wurde mir von einem Studenten empfohlen: <a href="http://www.java-blog-buch.de/inhaltsverzeichnis/">Java Blog Buch</a></p> <p>Aber hier sind <a href="../learning-java/">Video-Tutorials</a> zu finden.</p> <p>Ich habe gerade <a href="http://www.javatutorialhub.com/java-platform.html">javatutorialhub.com</a> gefunden. Das erweckt auch einen guten ersten Eindruck.</p> <p>Auf Udacity, einer Online-Universität, gibt es eine <a href="https://www.udacity.com/course/cs046">Einführung in die Programmierung mit Java</a>.</p> <h2>Artikel</h2> <p>Ich habe ein paar Artikel geschrieben, die für euch interessant sein könnten:</p> <ul> <li><a href="../tribonacci-folge/">Tribonacci-Folge</a></li> <li><a href="../how-to-sort-with-java/">How to sort with Java?</a></li> </ul> <h2>Links</h2> <h3>Uni-Links</h3> <ul> <li><a href="https://praktomat.info.uni-karlsruhe.de/">Praktomat</a></li> <li><a href="http://baldur.iti.uka.de/programmieren/">Folien, Übungsblätter und Checkstyle</a> (offiziell)</li> <li><a href="http://verialg.iti.kit.edu/english/583.php">Carsten Sinz</a></li> <li><a href="https://praktomat.info.uni-karlsruhe.de/praktomat_2012_WS_Abschluss">Abschlussaufgaben-Praktomat</a> (nur über VPN/KIT-Netz)</li> </ul> <h3>Weiterführende Links</h3> <ul> <li><a href="http://docs.oracle.com/javase/7/docs/">JavaDoc</a> und <a href="http://docs.oracle.com/javase/7/docs/api/">Java API</a></li> <li><a href="http://stackoverflow.com/">StackOverflow</a></li> <li><a href="http://www.youtube.com/watch?v=aAb7hSCtvGw">How To Design A Good API and Why it Matters</a></li> </ul> <h2>Für Tutoren</h2> <p>Das SVN ist hier: <code>https://s_thoma@svnserver.informatik.kit.edu/i12/svn/VeriAlg</code> Wobei ihr natürlich s_thoma durch euren ATIS-Account ersetzen müsst.</p> C Puzzle #2 //martin-thoma.com/c-puzzle-2/ Sat, 20 Oct 2012 17:00:53 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/c-puzzle-2 <p>What is the output of the following script? Why? How can it be fixed to get the expected output?</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#define __STDC_FORMAT_MACROS</span> <span class="cp">#include &lt;inttypes.h&gt;</span> <span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">uint64_t</span> <span class="n">testvar</span><span class="p">;</span> <span class="n">testvar</span> <span class="o">=</span> <span class="mi">1</span><span class="o">&lt;&lt;</span><span class="mi">30</span><span class="p">;</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;2^30 = %&quot;</span> <span class="n">PRIu64</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">testvar</span><span class="p">);</span> <span class="n">testvar</span> <span class="o">=</span> <span class="mi">1</span><span class="o">&lt;&lt;</span><span class="mi">31</span><span class="p">;</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;2^31 = %&quot;</span> <span class="n">PRIu64</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">testvar</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-text" data-lang="text">2^30 = 1073741824 2^31 = 18446744071562067968</code></pre></div> <h2>Expected output</h2> <div class="highlight"><pre><code class="language-text" data-lang="text">2^30 = 1073741824 2^31 = 2147483648</code></pre></div> <h2>Explanation</h2> <p><code>1&lt;&lt;30</code> does a bitshift for <code>int</code>, not for <code>uint64_t</code></p> <h2>How to fix it</h2> <p>Add a typecast:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#define __STDC_FORMAT_MACROS</span> <span class="cp">#include &lt;inttypes.h&gt;</span> <span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">uint64_t</span> <span class="n">testvar</span><span class="p">;</span> <span class="n">testvar</span> <span class="o">=</span> <span class="mi">1</span><span class="o">&lt;&lt;</span><span class="mi">30</span><span class="p">;</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;2^30 = %&quot;</span> <span class="n">PRIu64</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">testvar</span><span class="p">);</span> <span class="n">testvar</span> <span class="o">=</span> <span class="p">((</span><span class="kt">uint64_t</span><span class="p">)</span> <span class="mi">1</span><span class="p">)</span><span class="o">&lt;&lt;</span><span class="mi">31</span><span class="p">;</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;2^31 = %&quot;</span> <span class="n">PRIu64</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">testvar</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> Review des Acer Travelmate 5744Z //martin-thoma.com/review-des-acer-travelmate-5744z/ Fri, 19 Oct 2012 18:57:30 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/review-des-acer-travelmate-5744z <p>Vor ein paar Tagen ist mein <span itemprop="name">Acer Travelmate 5744Z</span>, das ich bei Amazon für <span itemprop="offers" itemscope="" itemtype="http://schema.org/Offer"><span itemprop="price">305,95</span> <span itemprop="priceCurrency">Euro</span></span> bekommen habe, angekommen. Ich habe es mit „Linux“ als System gekauft. Wie sich herausstellte, ist MeeGo release 1.0 mit dem Kernel 2.6.37, installiert. Das System startet zwar in sensationellen 29 Sekunden, aber Ubuntu ist mir doch lieber.</p> <p>edit: <em>argh</em> - also mit Ubuntu 12.04 (und Lubuntu 12.04 sowie Ubuntu mit Gnome/Gnome Classic/Cinnamon) bin ich nicht zufrieden. Windows 7 hat tatsächlich, ganz im Gegensatz zu allen Ubuntu-Arten, die Treiber CD benötigt. Naja.</p> <h2 id="technische-daten">Technische Daten</h2> <p><strong>Prozessor</strong>: Intel Pentium P6200 mit 2.13 GHz, 2 Kerne, 3 MB Cache (Quelle: <a href="http://ark.intel.com/products/50176/Intel-Pentium-Processor-P6200-3M-Cache-2_13-GHz">ark.intel.com</a>)</p> <p><strong>Arbeitsspeicher</strong>: 4GB DDR3 (3704 MiB laut lshw)</p> <p><strong>Harddisk</strong>: WDC WD3200BPVT-2 (320 GB, 5400 RPM, 2.5-inch, 8MB cache)</p> <p><strong>Display</strong>: 15,6” mit max. 1366px x 768px. Matt, LED LCD; Maximale Helligkeit von 174 cd/m² laut<a href="http://www.notebookcheck.com/Test-Acer-TravelMate-5744Z-P624G50Mikk-Notebook.71588.0.html">notebookcheck.com</a></p> <p><strong>Grafikkarte</strong>: Intel HD Graphics (onboard) - Intel GMA HD</p> <p><strong>Laufwerk</strong>: DVD-Super Multi DL drive</p> <p><strong>LAN</strong>: NetLink BCM57780 Gigabit Ethernet PCIe, capacity: 1Gbit/s</p> <p><strong>Gewicht</strong>: 2.5kg</p> <p><strong>Akku</strong>: vermutlich 4.400 mAh</p> <p><strong>Akkulaufzeit</strong>: 3.7 Std</p> <p><strong>B x H x T</strong>: 38.1 cm x 2.57 - 3.38 cm x 25.3 cm</p> <p><strong>Weiteres</strong>:</p> <ul> <li>Acer Nplify 802.11b/g/n: <blockquote>Acer Nplify, a high-throughput wireless solution, delivers superior performance and reliable connections while enabling emerging voice, video and data applications.</blockquote> </li> <li>SD-Kartenleser</li> <li>3x USB 2.0</li> <li>2,5 kg</li> <li>DVD-Brenner ist irgendwie nicht so toll zu öffnen. Das war beim 5735Z besser.</li> </ul> <h2 id="linux-sorgenkinder">Linux Sorgenkinder</h2> <ul> <li><strong>Webcam</strong>: Funktioniert out of the box</li> <li><strong>WLAN</strong>: Funktioniert out of the box (WTF, ich kann bei mir das Uni-WLAN sehen!?! - Ein AR9485 Wireless Network Adapter von Atheros Communications Inc.)</li> <li><strong>Sound</strong>: Funktioniert out of the box (Lautsprecher und Buchse - die Lautsprecher sind nicht so toll, aber das ist bei einem Notebook ja zu erwarten)</li> <li><strong>Mikrofon</strong>: Sehr leise, funktioniert aber out of the box</li> </ul> <h2>Fazit</h2> <p>Tolles Low-Budget Notebook, das einwandfrei unter Linux (und Windows) funktioniert!</p> <p>Was ich gerne noch hätte (aber bei diesem Preis nicht erwarten darf): Bluetooth</p> <p>Ich habe auch direkt einen <a href="http://linuxhcl.com/browse/product?id=7811">Eintrag in die HCL</a> gemacht.</p> Java Puzzle #13: Absolute value weirdness //martin-thoma.com/java-puzzle-13-absolute-value-weirdness/ Fri, 19 Oct 2012 17:00:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-13-absolute-value-weirdness <p>What does the following snippet output?</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">SomeClass</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">a</span> <span class="o">=</span> <span class="o">-</span><span class="mi">10</span><span class="o">;</span> <span class="kt">int</span> <span class="n">b</span> <span class="o">=</span> <span class="o">-</span><span class="mi">2147483648</span><span class="o">;</span> <span class="c1">// -2147483648 == -2**31</span> <span class="k">if</span> <span class="o">(</span><span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">a</span><span class="o">)</span> <span class="o">&lt;</span> <span class="o">-</span><span class="mi">1</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|a| &lt; -1&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|a| &gt;= -1&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">if</span> <span class="o">(</span><span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">b</span><span class="o">)</span> <span class="o">&lt;</span> <span class="o">-</span><span class="mi">1</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|b| &lt; -1&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|b| &gt;= -1&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|a| = &quot;</span> <span class="o">+</span> <span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">a</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|b| = &quot;</span> <span class="o">+</span> <span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">b</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-text" data-lang="text">|a| &gt;= -1 |b| &lt; -1 |a| = 10 |b| = -2147483648</code></pre></div> <h2>Explanation</h2> <p>Integer values range (in Java) from -2147483648 to 2147483647. This means, the absolute value of -2147483648 is not in the integer range. For more details, see <a href="http://stackoverflow.com/a/5444634/562769">this SO answer</a>.</p> Bürokratie am KIT //martin-thoma.com/burokratie-am-kit/ Wed, 17 Oct 2012 18:06:31 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/burokratie-am-kit <p>Das KIT sieht sich gerne als Elite-Universität.<sup>[<a href="http://www.kit.edu/besuchen/pi_2012_11933.php">1</a>]</sup> Es werden Rankings in Vorlesungen zitiert und erst vor kurzem wurde von einigen Professoren in der Vorlesung der Verlust des Status der Elite-Universität betrauert.<sup>[<a href="http://bildungsklick.de/a/84162/hippler-elite-verlust-herber-rueckschlag-fuer-kit/">1</a>]</sup> Ich weiß nicht, was die Kriterien für eine Elite-Uni nach der Exzellenzinitiative sind, aber ich kann mir einige notwendige Voraussetzungen vorstellen, die für mich eine Elite-Uni ausmachen:</p> <ul> <li>Lehre <ul> <li>Vorlesungen, die anspruchsvollen Stoff gut strukturiert und aufbereitet vermitteln</li> <li>&Uuml;bungen, die den Stoff vertiefen und eventuell motivieren</li> <li>Tutorien, die offene Fragen beantworten und von kompetenten Tutoren gehalten werden</li> </ul> </li> <li>Forschung: Hier kann ich mir nicht anma&szlig;en, gute Kriterien aufstellen zu k&ouml;nnen, da ich selbst noch nicht daran beteiligt bin.</li> <li>Wirtschaft: vgl. Forschung</li> </ul> <p>Damit die Personen, die an Lehre, Forschung und in der Wirtschaft beteiligt sind gut arbeiten können, muss die Organisation reibungsfrei verlaufen. Mir ist klar, dass bei 22.552 Studierenden (Stand: März 2012) nicht immer alles reibungsfrei ablaufen kann. Auch der Bologna-Prozess scheint wohl immer noch Probleme nach sich zu ziehen. Aber für ein paar Probleme, die ich vor kurzem selbst erleben musste, habe ich kein Verständnis. Diese Probleme sind - so scheint es mir - bürokratischer und organisatorischer Natur:</p> <h2>Studienb&uuml;ro</h2> <p>Das <a href="http://www.kit.edu/studieren/1960.php">Studienbüro</a> hat folgende Öffnungszeiten:</p> <ul> <li>Mo-Mi: 10:00 - 12:00 Uhr</li> <li>Do: 13:30 - 15:30 Uhr</li> </ul> <p>Es hat also in der Woche nur 8 Stunden geöffnet. Ich war heute (Mittwoch) um 9:40 Uhr Studienbüro und es war bereits eine Schlange von ca. 20 Leuten vor der Tür. Als pünktlich um 10:00 Uhr der Eingang geöffnet wurde, reichte die Schlange bereits bis zum gegenüberliegenden Gebäude. Man muss nun beobachten, wie sich das im laufe des Semesters verhält, aber es ist schon ein deutliches Indiz dafür, dass hier entweder Mängel in der Organisation und Struktur des Studiums bzw. der damit verbundenen Software (z.B. QISPOS) vorliegen, oder zu wenig Personal vorhanden ist.</p> <h3>Schalter und Schlangen</h3> <p>Momentan sind Zettelrollen in verschiedenen Farben aufgestellt. Die Farben sind je nach Studiengang unterschiedlich. Auf jedem Zettel steht eine Nummer und diese wird aufgerufen. Dazu steht eine Frau an der Tür, ruft die Nummer und hält die Tür auf.</p> <p>Ich weiß nicht ob diese Frau noch irgendetwas anderes macht, aber es scheint nicht der Fall zu sein. Wenn sie in dieser Zeit einen weiteren Schalter betreuen würde und das Aufrufen wie bei der Bahn oder im Finanzamt über eine elektronische Anzeige geschehen würde, hätte man vermutlich schon eine Effizienzsteigerung. Die aktuelle Nummer könnte man dann auch über einen Webdienst verfügbar machen, sodass man in der Zwischenzeit auch etwas sinnvolleres machen kann.</p> <p>Nach ein paar Minuten wurde gefragt: “Gibt es noch irgendjemanden der einen blauen Zettel hat?”. Es gab niemanden. Was passiert dann? Ist eine Arbeitskraft dann untätig, obwohl noch 50 Leute auf Hilfe / Antworten warten?</p> <h3>Freundlichkeit und Kompetenz</h3> <p>Als ich dann endlich im Studienbüro zu meinem Schalter gekommen bin, konnte ich mein Problem vorstellen. Ich versuche das möglichst wortwörtlich wiederzugeben:</p> <ol> <li>Das Modul “Algorithmen I” war nicht als bestanden markiert, obwohl ich die Klausur “Algorithmen I” bestanden habe, diese auch als bestanden im System stand und es keine weiteren Voraussetzungen gibt. Das habe ich der Angestellten so gesagt. Angestellte: „Da kann ich nichts machen, ich brauche erst ein Formular. Ohne Formular geht da nichts, da müssen sie zu Frau Gheta, ich muss 3 Schalter betreuen und habe dafür keine Zeit.“</li> </ol> <p>Was soll denn das? Ein kurzer Blick ins Modulhandbuch - ich konnte auch sagen an welcher Stelle - ein Blick auf meine Leistungen (die sie bereits aufgerufen hatte) und alles wäre klar geweisen. Also habe ich das Problem nochmals beschrieben Ich: „Ich habe alle Teile des Moduls bestanden, warum ist dann das Modul nicht als bestanden markiert?“ Sie schaut in ihr System und sagt mir, dass ich noch nicht alles aus der Theoretischen Informatik bestanden habe. Warum hat sie plötzlich mit theoretischer Informatik angefangen? Ich habe nichts von Theoretischer Informatik gesagt und mir ist klar, dass ich für das Fach noch nicht alles bestanden habe. Aber das hat doch nichts mit dem Modul zu tun.</p> <ol> <li>Obwohl ich die Übungsscheine „Lineare Algebra I“ und „Lineare Algebra II“ für Mathematiker gemacht und bestanden habe, ist nur ein Übungsschein „Lineare Algebra I für die fachrichtung Informatik“ in QISPOS. Also sollte der Übungsschein „Lineare Algebra I für die fachrichtung Informatik“ in „Lineare Algebra I“ umgewandelt werden und der Übungsschein „Lineare Algebra II“ hinzugefügt werden. Ich habe beide Scheine in Papierform, vom Prof. unterschrieben, dabei gehabt und ihr gegeben. Angestellte legt die beiden Übungsschein-Bestätigungen auf einen Ablagestapel Angestellte: „Dafür benötigen sie eine Bestätigung.“ Ich: „Aber ich habe Ihnen doch gerade die Bestätigung gegeben?!?“ Angestellte: „Für eine Ummeldung muss ein anderes Formular ausgefüllt werden. Ich kann so nur die Übungsscheine hinzufügen.“ Na gut, dann habe ich nun wohl einen Übungsschein zu viel … Nach ein bisschen Diskutieren meint sie, ich hätte wegen HM bereits einen Antrag gemacht. Ich habe niemals HM besucht und hatte bisher auch keine Probleme wegen HM vs. Analysis. Hoffentlich kommt das jetzt nicht dazu …</li> </ol> <p>Insgesamt muss ich sagen, wurde ich unfreundlich behandet - ich hatte das Gefühl, direkt wieder rausgeworfen zu werden - und die Frau hat mir nicht zugehört. Kurz darauf bin ich zum „Servicezentrum für Studium und Lehre“ gegangen. Dort hat mir Frau Metzig geholfen. Sie hat mein Problem verstanden. Nach wenigen Minuten, ohne langes Anstehen oder irgendwelche Formulare hat sie mir versichert, dass Sie sich um das Problem in den nächsten zwei Tagen kümmert. Schon nach 2 Stunden kam eine E-Mail an, in der sie mir mitteilte, dass es ein Systemfehler war. Mein Problem ist nun behoben.</p> <h2>QISPOS</h2> <p>QISPOS ist ein System von der <a href="http://de.wikipedia.org/wiki/Hochschul-Informations-System">HIS Hochschul-Informations-System GmbH</a>, das am KIT für die Prüfungsverwaltung eingesetzt wird. Das bedeutet, hier meldet man sich an und ab, kann Noten und bestandene Module nachschauen. Auch Voraussetzungen für andere Module wie z.B. PSE werden hiermit überprüft.</p> <p>Dieses System muss ziemlich schwere Voraussetzungen erfüllen: Es muss funktionieren. Immer. Leider ist das nicht der Fall:</p> <ul> <li>Pr&uuml;fungsanmeldungen klappen nicht. Es werden fehlende Voraussetzungen angezeigt, obwohl es keine Voraussetzungen gibt (ist mir mit Algorithmen passiert)</li> <li>Die Anmeldung f&uuml;r manche Module ist nicht m&ouml;glich, obwohl sie laut Modulhandbuch m&ouml;glich ist (z.B. Physiker und Mathe)</li> <li>Sonstige Systemfehler kommen vor: Das Modul Algorithmen wurde bei mir nicht als bestanden markiert, obwohl es offensichtlich bestanden war.</li> </ul> <p>Das sind jetzt nur ein paar Fehler, die mir persönlich passiert sind. Es gibt bestimmt noch mehr. Und von unschönen Dingen wie langen Ladezeiten, einer schlechten Menüführung oder einer fehlenden Suchfunktion will ich mal gar nicht reden.</p> <p>Da frage ich mich schon, was das KIT dafür bezahlt. Einfach gesagt, sehe ich zwei Möglichkeiten:</p> <ol> <li>Es wird sehr wenig bezahlt: Dann ist es kein Wunder, dass diese Probleme auftreten. Dann sollte man sich &uuml;berlegen, ob es nicht sinnvoll w&auml;re, mehr zu investieren</li> <li>Man zahlt angemessen / viel f&uuml;r die geforderten Eigenschaften: In diesem Fall sollte man sich nach einem anderem Anbieter umsehen oder selbst eine Entwicklung starten.</li> </ol> <p>Ehrlich gesagt wundert es mich, dass es hierfür keine Uni-Eigene Lösung gibt. Gibt es OpenSource in diesem Bereich?</p> <h2>H&auml;ufige Probleme - FAQ</h2> <p>Als ich gewartet habe, sind mir zwei häufige Probleme aufgefallen:</p> <ul> <li>Defekte KIT-Card</li> <li>Keine Matrikelnummer</li> </ul> <p>Eine defekte KIT-Card sollte einfach über ein Online-Formular nachbestellbar sein. Ich sehe keinen Grund, warum man dazu in das Studienbüro gehen sollte.</p> <p>Wenn jetzt, nach beginn der Vorlesungszeit, noch keine Matrikelnummer vorhanden ist, läuft irgendwas schief. Da es bei vielen der Fall ist, kann es nicht an den Studenten liegen. Entweder wurden bestimmte voraussetzungen nicht deutlich genug gemacht (à la: Es muss Formular XY zurückgeschickt werden, bevor eine Matrikelnummer ausgestellt wird), oder es der Prozess eine Matrikelnummer zu erstellen dauert zu lange. Falls das zu lange dauert, kann man entweder den Prozessablauf beschleunigen, oder mehr Personal einstellen.</p> <p>Eine einfache FAQ-Liste auf der Seite des Studienbüros könnte schon helfen.</p> <p>So, jetzt habe ich einige Stunden mit Bürokratie, Organisation und diesem Bericht darüber verbacht und etwas Frust abgebaut. Zeit, die ich in mein Studium hätte stecken können. Vielleicht liest es ja jemand, der etwas ändern kann.</p> <p>Habt ihr ähnliche Geschichten mit dem Studienbüro erlebt? Habt ihr Verbesserungsvorschläge? Dann hinterlasst doch einfach einen Kommentar.</p> Java Puzzle #12: Control-flow //martin-thoma.com/java-puzzle-12-control-flow/ Wed, 17 Oct 2012 17:00:19 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-12-control-flow <p>What is the output of the following <strong>HelloWorld.java</strong>?</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">HelloWorld</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="mi">2</span> <span class="o">&lt;</span> <span class="mi">1</span><span class="o">);</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Yes&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . .</p> <h2>Answer</h2> <p>The output is “Yes”.</p> <h2>Explanation</h2> <p>The <code>;</code> means, that no block is executed. The <code>{ ... }</code> is just a code block and not really related to the <code>if</code>-statement.</p> Learning Java //martin-thoma.com/learning-java/ Mon, 15 Oct 2012 17:00:04 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/learning-java <p>I’ve just found some YouTube clips by <a href="http://www.youtube.com/user/thenewboston">thenewboston</a> in which he explains how to program in Java. I didn’t watch them, but I took a look at some of them. Seems to be very easy to understand.</p> <p>He starts right from the beginning (that means: how do I install Java?) explains basic concepts like variables, program flow statements and user input and goes to GUI with Swing:</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/videoseries?list=PLFE2CE09D83EE3E28&amp;hl=en_US" frameborder="0" allowfullscreen=""></iframe> <h2>See also</h2> <ul> <li><a href="http://www.youtube.com/playlist?list=PLA68C1F33757B4A38">C++ Beginner Tutorial</a>: 54 Videos on YouTube from XoaX.net</li> <li><a href="http://www.youtube.com/playlist?list=PLA68C1F33757B4A38">C++ OpenGL Beginner Tutorials</a>: 54 Videos from XoaX.net</li> </ul> Java Puzzle #11: Change argument of foreach //martin-thoma.com/java-puzzle-11-change-argument-of-foreach/ Sun, 14 Oct 2012 21:15:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-11-change-argument-of-foreach <p>What is the output of the following HelloWorld.java?</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.LinkedList</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">HelloWorld</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">list</span> <span class="o">=</span> <span class="k">new</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">2</span><span class="o">);</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">3</span><span class="o">);</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="n">Integer</span> <span class="n">el</span> <span class="o">:</span> <span class="n">list</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">el</span><span class="o">);</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">el</span><span class="o">);</span> <span class="n">i</span><span class="o">++;</span> <span class="k">if</span> <span class="o">(</span><span class="n">i</span> <span class="o">&gt;</span> <span class="mi">20</span><span class="o">)</span> <span class="o">{</span> <span class="k">break</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="mi">1</span> <span class="n">Exception</span> <span class="n">in</span> <span class="n">thread</span> <span class="s">&quot;main&quot;</span> <span class="n">java</span><span class="o">.</span><span class="na">util</span><span class="o">.</span><span class="na">ConcurrentModificationException</span> <span class="n">at</span> <span class="n">java</span><span class="o">.</span><span class="na">util</span><span class="o">.</span><span class="na">LinkedList</span><span class="err">`</span><span class="n">$ListItr</span><span class="o">.</span><span class="na">checkForComodification</span><span class="o">(</span><span class="n">LinkedList</span><span class="o">.</span><span class="na">java</span><span class="o">:</span><span class="mi">761</span><span class="o">)</span> <span class="n">at</span> <span class="n">java</span><span class="o">.</span><span class="na">util</span><span class="o">.</span><span class="na">LinkedList$</span><span class="err">`</span><span class="n">ListItr</span><span class="o">.</span><span class="na">next</span><span class="o">(</span><span class="n">LinkedList</span><span class="o">.</span><span class="na">java</span><span class="o">:</span><span class="mi">696</span><span class="o">)</span> <span class="n">at</span> <span class="n">HelloWorld</span><span class="o">.</span><span class="na">main</span><span class="o">(</span><span class="n">HelloWorld</span><span class="o">.</span><span class="na">java</span><span class="o">:</span><span class="mi">10</span><span class="o">)</span></code></pre></div> Manipulating PDF files //martin-thoma.com/manipulating-pdf-files/ Sat, 13 Oct 2012 10:24:01 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/manipulating-pdf-files <p>I just wanted to get some pages out of a bigger PDF file. The tool that can be used for this task is called <code>pdftk</code>. It is in the standard Ubuntu repsitory.</p> <h2>Usage</h2> <p>Split the file, so that every page becomes a new PDF file:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pdftk myfile.pdf burst</code></pre></div> <p>Extract pages 10 to 12 from <tt>bigPDF.pdf</tt>:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pdftk bigPDF.pdf cat 10-12 output output.pdf</code></pre></div> Java Generics //martin-thoma.com/java-generics/ Wed, 10 Oct 2012 12:18:42 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-generics <p>Some months ago, I had to improve some Java code for university. They gave us a model of a windows like file system and we had to make the code “cleaner”. I think I’ve overdone the application of generics, but it’s a nice example for generics ;-)</p> <p>You can download the <a href="../images/2012/10/Filesystem.zip">complete Eclipse project</a>.</p> <h2>Computer.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.Vector</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Computer</span> <span class="o">{</span> <span class="kd">public</span> <span class="n">String</span> <span class="n">computerName</span><span class="o">;</span> <span class="kd">public</span> <span class="n">Vector</span><span class="o">&lt;</span><span class="n">HDD</span><span class="o">&gt;</span> <span class="n">hdds</span> <span class="o">=</span> <span class="k">new</span> <span class="n">Vector</span><span class="o">&lt;</span><span class="n">HDD</span><span class="o">&gt;();</span> <span class="kd">public</span> <span class="nf">Computer</span><span class="o">(</span><span class="n">String</span> <span class="n">companyName</span><span class="o">,</span> <span class="n">HDD</span> <span class="n">gf</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">computerName</span> <span class="o">=</span> <span class="n">companyName</span><span class="o">;</span> <span class="k">this</span><span class="o">.</span><span class="na">hdds</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">gf</span><span class="o">);</span> <span class="o">}</span> <span class="kd">private</span> <span class="kt">void</span> <span class="nf">addDrive</span><span class="o">(</span><span class="n">HDD</span> <span class="n">drive</span><span class="o">)</span> <span class="o">{</span> <span class="n">hdds</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">drive</span><span class="o">);</span> <span class="o">}</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">printContent</span><span class="o">()</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="n">HDD</span> <span class="n">hdd</span> <span class="o">:</span> <span class="n">hdds</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;| HDD: &quot;</span> <span class="o">+</span> <span class="n">hdd</span><span class="o">.</span><span class="na">getName</span><span class="o">()</span> <span class="o">+</span> <span class="s">&quot; (&quot;</span> <span class="o">+</span> <span class="n">hdd</span><span class="o">.</span><span class="na">getDescription</span><span class="o">()</span> <span class="o">+</span> <span class="s">&quot;)&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">Directory</span> <span class="n">dir</span> <span class="o">:</span> <span class="n">hdd</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">Directory</span><span class="o">.</span><span class="na">class</span><span class="o">))</span> <span class="o">{</span> <span class="n">printContent</span><span class="o">(</span><span class="n">dir</span><span class="o">,</span> <span class="s">&quot;&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">for</span> <span class="o">(</span><span class="n">ZipArchiv</span> <span class="n">zip</span> <span class="o">:</span> <span class="n">hdd</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">ZipArchiv</span><span class="o">.</span><span class="na">class</span><span class="o">))</span> <span class="o">{</span> <span class="n">printContent</span><span class="o">(</span><span class="n">zip</span><span class="o">,</span> <span class="s">&quot;&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">for</span> <span class="o">(</span><span class="n">File</span> <span class="n">f</span> <span class="o">:</span> <span class="n">hdd</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">File</span><span class="o">.</span><span class="na">class</span><span class="o">))</span> <span class="o">{</span> <span class="n">printContent</span><span class="o">(</span><span class="n">f</span><span class="o">,</span> <span class="s">&quot;|-&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="kd">private</span> <span class="kt">void</span> <span class="nf">printContent</span><span class="o">(</span><span class="n">Node</span> <span class="n">d</span><span class="o">,</span> <span class="n">String</span> <span class="n">ident</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;|-&quot;</span> <span class="o">+</span> <span class="n">ident</span> <span class="o">+</span> <span class="s">&quot; &quot;</span> <span class="o">+</span> <span class="n">d</span><span class="o">.</span><span class="na">getName</span><span class="o">());</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Class</span><span class="o">&lt;?</span> <span class="kd">extends</span> <span class="n">Node</span><span class="o">&gt;&gt;</span> <span class="n">list</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Class</span><span class="o">&lt;?</span> <span class="kd">extends</span> <span class="n">Node</span><span class="o">&gt;&gt;();</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">Directory</span><span class="o">.</span><span class="na">class</span><span class="o">);</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">ZipArchiv</span><span class="o">.</span><span class="na">class</span><span class="o">);</span> <span class="n">list</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">File</span><span class="o">.</span><span class="na">class</span><span class="o">);</span> <span class="k">if</span> <span class="o">(</span><span class="n">d</span> <span class="k">instanceof</span> <span class="n">NodeContainer</span><span class="o">)</span> <span class="o">{</span> <span class="n">NodeContainer</span> <span class="n">e</span> <span class="o">=</span> <span class="o">(</span><span class="n">NodeContainer</span><span class="o">)</span> <span class="n">d</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="n">Class</span><span class="o">&lt;?</span> <span class="kd">extends</span> <span class="n">Node</span><span class="o">&gt;</span> <span class="n">T</span> <span class="o">:</span> <span class="n">list</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;?</span> <span class="kd">extends</span> <span class="n">Node</span><span class="o">&gt;</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">e</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">T</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">Node</span> <span class="n">n</span> <span class="o">:</span> <span class="n">tmp</span><span class="o">)</span> <span class="o">{</span> <span class="n">printContent</span><span class="o">(</span><span class="n">n</span><span class="o">,</span> <span class="n">ident</span> <span class="o">+</span> <span class="s">&quot;-&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="c1">// Create the computer</span> <span class="n">HDD</span> <span class="n">platte1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">HDD</span><span class="o">(</span><span class="s">&quot;C&quot;</span><span class="o">,</span> <span class="s">&quot;Main disk&quot;</span><span class="o">);</span> <span class="n">Computer</span> <span class="n">f</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Computer</span><span class="o">(</span><span class="s">&quot;MyMainComputer&quot;</span><span class="o">,</span> <span class="n">platte1</span><span class="o">);</span> <span class="c1">// we need a backup</span> <span class="n">HDD</span> <span class="n">platte2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">HDD</span><span class="o">(</span><span class="s">&quot;D&quot;</span><span class="o">,</span> <span class="s">&quot;Backup disk&quot;</span><span class="o">);</span> <span class="n">f</span><span class="o">.</span><span class="na">addDrive</span><span class="o">(</span><span class="n">platte2</span><span class="o">);</span> <span class="c1">// create main directories</span> <span class="n">Directory</span> <span class="n">v1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Directory</span><span class="o">(</span><span class="s">&quot;temp&quot;</span><span class="o">,</span> <span class="s">&quot;temporary files&quot;</span><span class="o">);</span> <span class="n">platte1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">v1</span><span class="o">);</span> <span class="n">v1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="k">new</span> <span class="nf">Directory</span><span class="o">(</span><span class="s">&quot;asdf&quot;</span><span class="o">,</span> <span class="s">&quot;jkl&amp;ouml;&quot;</span><span class="o">));</span> <span class="n">Directory</span> <span class="n">v2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Directory</span><span class="o">(</span><span class="s">&quot;Pictures&quot;</span><span class="o">,</span> <span class="s">&quot;Holiday pictures&quot;</span><span class="o">);</span> <span class="n">platte1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">v2</span><span class="o">);</span> <span class="c1">// Gib den Verzeichnissen ein paar Inhalte</span> <span class="c1">// Ein paar Archive im Temp</span> <span class="n">ZipArchiv</span> <span class="n">zip1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">ZipArchiv</span><span class="o">(</span><span class="s">&quot;fp-update.zip&quot;</span><span class="o">,</span> <span class="s">&quot;Flashplayer Update&quot;</span><span class="o">);</span> <span class="n">v1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">zip1</span><span class="o">);</span> <span class="n">ZipArchiv</span> <span class="n">zip2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">ZipArchiv</span><span class="o">(</span><span class="s">&quot;swt1-folien.zip&quot;</span><span class="o">,</span> <span class="s">&quot;PDFs of SWT1&quot;</span><span class="o">);</span> <span class="n">v1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">zip2</span><span class="o">);</span> <span class="c1">// pictures</span> <span class="n">ZipArchiv</span> <span class="n">barcelona</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">ZipArchiv</span><span class="o">(</span><span class="s">&quot;2010-Barcelona.zip&quot;</span><span class="o">,</span> <span class="s">&quot;Holiday Barcelona 2010&quot;</span><span class="o">);</span> <span class="n">v2</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">barcelona</span><span class="o">);</span> <span class="n">ZipArchiv</span> <span class="n">mallorca</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">ZipArchiv</span><span class="o">(</span><span class="s">&quot;2011-Mallorca.zip&quot;</span><span class="o">,</span> <span class="s">&quot;Sonne satt&quot;</span><span class="o">);</span> <span class="n">v2</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">mallorca</span><span class="o">);</span> <span class="n">v2</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;ipdlogo.png&quot;</span><span class="o">,</span> <span class="s">&quot;IPD&quot;</span><span class="o">));</span> <span class="c1">// add some files to archives</span> <span class="n">ZipArchiv</span> <span class="n">b1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">ZipArchiv</span><span class="o">(</span><span class="s">&quot;BarcelonaBeach.zip&quot;</span><span class="o">,</span> <span class="s">&quot;Strandbilder&quot;</span><span class="o">);</span> <span class="n">barcelona</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">b1</span><span class="o">);</span> <span class="n">b1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;s1.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Strand&quot;</span><span class="o">));</span> <span class="n">b1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;s2.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Mehr Strand&quot;</span><span class="o">));</span> <span class="n">b1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;s3.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Strand und Meer&quot;</span><span class="o">));</span> <span class="n">b1</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;s4.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Noch mehr Strand&quot;</span><span class="o">));</span> <span class="n">File</span> <span class="n">b2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;Picasso.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Museum&quot;</span><span class="o">);</span> <span class="n">barcelona</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">b2</span><span class="o">);</span> <span class="n">File</span> <span class="n">b3</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;SagradaFamilia.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Kirche&quot;</span><span class="o">);</span> <span class="n">barcelona</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">b3</span><span class="o">);</span> <span class="n">File</span> <span class="n">b4</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;CampNou.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Fu&amp;szlig;ball&quot;</span><span class="o">);</span> <span class="n">barcelona</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">b4</span><span class="o">);</span> <span class="n">File</span> <span class="n">m1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">File</span><span class="o">(</span><span class="s">&quot;Strand.jpg&quot;</span><span class="o">,</span> <span class="s">&quot;Strand&quot;</span><span class="o">);</span> <span class="n">mallorca</span><span class="o">.</span><span class="na">addNode</span><span class="o">(</span><span class="n">m1</span><span class="o">);</span> <span class="n">f</span><span class="o">.</span><span class="na">printContent</span><span class="o">();</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Node.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">abstract</span> <span class="kd">class</span> <span class="nc">Node</span> <span class="o">{</span> <span class="kd">private</span> <span class="n">String</span> <span class="n">name</span><span class="o">;</span> <span class="kd">private</span> <span class="n">String</span> <span class="n">description</span><span class="o">;</span> <span class="kd">public</span> <span class="n">String</span> <span class="nf">getName</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">name</span><span class="o">;</span> <span class="o">}</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">setName</span><span class="o">(</span><span class="n">String</span> <span class="n">name</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">name</span> <span class="o">=</span> <span class="n">name</span><span class="o">;</span> <span class="o">}</span> <span class="kd">public</span> <span class="n">String</span> <span class="nf">getDescription</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">description</span><span class="o">;</span> <span class="o">}</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">setDescription</span><span class="o">(</span><span class="n">String</span> <span class="n">description</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">description</span> <span class="o">=</span> <span class="n">description</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>NodeContainer.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">interface</span> <span class="nc">NodeContainer</span> <span class="o">{</span> <span class="kd">public</span> <span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="nf">get</span><span class="o">(</span><span class="n">Class</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">clazz</span><span class="o">);</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">addNode</span><span class="o">(</span><span class="n">Node</span> <span class="n">n</span><span class="o">);</span> <span class="o">}</span></code></pre></div> <h2>HDD.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">HDD</span> <span class="kd">extends</span> <span class="n">Node</span> <span class="kd">implements</span> <span class="n">NodeContainer</span> <span class="o">{</span> <span class="kd">private</span> <span class="kd">final</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Node</span><span class="o">&gt;</span> <span class="n">nodes</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Node</span><span class="o">&gt;();</span> <span class="kd">public</span> <span class="nf">HDD</span><span class="o">(</span><span class="n">String</span> <span class="n">name</span><span class="o">,</span> <span class="n">String</span> <span class="n">beschreibung</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">setName</span><span class="o">(</span><span class="n">name</span><span class="o">);</span> <span class="k">this</span><span class="o">.</span><span class="na">setDescription</span><span class="o">(</span><span class="n">beschreibung</span><span class="o">);</span> <span class="o">}</span> <span class="nd">@SuppressWarnings</span><span class="o">(</span><span class="s">&quot;unchecked&quot;</span><span class="o">)</span> <span class="kd">public</span> <span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="nf">get</span><span class="o">(</span><span class="n">Class</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">clazz</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">allElements</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;();</span> <span class="k">for</span><span class="o">(</span><span class="n">Node</span> <span class="n">o</span> <span class="o">:</span> <span class="n">nodes</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">o</span><span class="o">.</span><span class="na">getClass</span><span class="o">()</span> <span class="o">==</span> <span class="n">clazz</span><span class="o">)</span> <span class="o">{</span> <span class="n">allElements</span><span class="o">.</span><span class="na">add</span><span class="o">((</span><span class="n">T</span><span class="o">)</span> <span class="n">o</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">allElements</span><span class="o">;</span> <span class="o">}</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">addNode</span><span class="o">(</span><span class="n">Node</span> <span class="n">n</span><span class="o">)</span> <span class="o">{</span> <span class="n">nodes</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">n</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Directory.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Directory</span> <span class="kd">extends</span> <span class="n">Node</span> <span class="kd">implements</span> <span class="n">NodeContainer</span> <span class="o">{</span> <span class="kd">private</span> <span class="kd">final</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Node</span><span class="o">&gt;</span> <span class="n">nodes</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Node</span><span class="o">&gt;();</span> <span class="kd">public</span> <span class="nf">Directory</span><span class="o">(</span><span class="n">String</span> <span class="n">name</span><span class="o">,</span> <span class="n">String</span> <span class="n">description</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">setName</span><span class="o">(</span><span class="n">name</span><span class="o">);</span> <span class="k">this</span><span class="o">.</span><span class="na">setDescription</span><span class="o">(</span><span class="n">description</span><span class="o">);</span> <span class="o">}</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">addNode</span><span class="o">(</span><span class="n">Node</span> <span class="n">n</span><span class="o">)</span> <span class="o">{</span> <span class="n">nodes</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">n</span><span class="o">);</span> <span class="o">}</span> <span class="nd">@SuppressWarnings</span><span class="o">(</span><span class="s">&quot;unchecked&quot;</span><span class="o">)</span> <span class="kd">public</span> <span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="nf">get</span><span class="o">(</span><span class="n">Class</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">clazz</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">allElements</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;();</span> <span class="k">for</span><span class="o">(</span><span class="n">Node</span> <span class="n">o</span> <span class="o">:</span> <span class="n">nodes</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">o</span><span class="o">.</span><span class="na">getClass</span><span class="o">()</span> <span class="o">==</span> <span class="n">clazz</span><span class="o">)</span> <span class="o">{</span> <span class="n">allElements</span><span class="o">.</span><span class="na">add</span><span class="o">((</span><span class="n">T</span><span class="o">)</span> <span class="n">o</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">allElements</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>ZipArchiv.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">ZipArchiv</span> <span class="kd">extends</span> <span class="n">File</span> <span class="kd">implements</span> <span class="n">NodeContainer</span> <span class="o">{</span> <span class="kd">private</span> <span class="kd">final</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Node</span><span class="o">&gt;</span> <span class="n">nodes</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Node</span><span class="o">&gt;();</span> <span class="kd">public</span> <span class="nf">ZipArchiv</span><span class="o">(</span><span class="n">String</span> <span class="n">name</span><span class="o">,</span> <span class="n">String</span> <span class="n">description</span><span class="o">)</span> <span class="o">{</span> <span class="kd">super</span><span class="o">(</span><span class="n">name</span><span class="o">,</span> <span class="n">description</span><span class="o">);</span> <span class="o">}</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">addNode</span><span class="o">(</span><span class="n">Node</span> <span class="n">n</span><span class="o">)</span> <span class="o">{</span> <span class="n">nodes</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">n</span><span class="o">);</span> <span class="o">}</span> <span class="nd">@SuppressWarnings</span><span class="o">(</span><span class="s">&quot;unchecked&quot;</span><span class="o">)</span> <span class="kd">public</span> <span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="nf">get</span><span class="o">(</span><span class="n">Class</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">clazz</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;</span> <span class="n">allElements</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">T</span><span class="o">&gt;();</span> <span class="k">for</span><span class="o">(</span><span class="n">Node</span> <span class="n">o</span> <span class="o">:</span> <span class="n">nodes</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">o</span><span class="o">.</span><span class="na">getClass</span><span class="o">()</span> <span class="o">==</span> <span class="n">clazz</span><span class="o">)</span> <span class="o">{</span> <span class="n">allElements</span><span class="o">.</span><span class="na">add</span><span class="o">((</span><span class="n">T</span><span class="o">)</span> <span class="n">o</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">allElements</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>File.java</h2> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">package</span> <span class="n">edu</span><span class="o">.</span><span class="na">kit</span><span class="o">.</span><span class="na">filesystem</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">File</span> <span class="kd">extends</span> <span class="n">Node</span> <span class="o">{</span> <span class="kd">public</span> <span class="nf">File</span><span class="o">(</span><span class="n">String</span> <span class="n">name</span><span class="o">,</span> <span class="n">String</span> <span class="n">beschreibung</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">setName</span><span class="o">(</span><span class="n">name</span><span class="o">);</span> <span class="k">this</span><span class="o">.</span><span class="na">setDescription</span><span class="o">(</span><span class="n">beschreibung</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> Balanzan Theme //martin-thoma.com/balanzan-theme/ Tue, 09 Oct 2012 18:20:35 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/balanzan-theme <p>I don’t understand why all desktop environment seem to lack a good theme chooser/editor and good themes. I have one favorite theme - called “<a href="http://www.bisigi-project.org/?p=28&amp;lang=en">Balanzan Theme</a>” which should be available in every distribution. The Balanzan Theme is part of the <a href="http://www.bisigi-project.org/?lang=en">bisigi-project</a>. According to <a href="https://launchpad.net/~bisigi/+archive/ppa/+files/balanzan-theme_1.8.1.natty.ppa1.tar.gz">the package</a>, it is licensed under GPL. So I think I can upload some of its content here.</p> <h2>Installation</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo add-apt-repository ppa:bisigi sudo apt-get update sudo apt-get install bisigi-themes</code></pre></div> <h2>Impression</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/10/balazan-font-300x247.png"><img src="../images/2012/10/balazan-font-300x247.png" alt="Impression of the Balanzan Theme" width="" height="" class="size-medium wp-image-46561" /></a><p class="wp-caption-text">Impression of the Balanzan Theme</p></div> <h2>Color Theme</h2> <h3>LXDE</h3> <table class="wikitable"> <tr> <th>&nbsp;</th> <th>Background</th> <th>Foreground</th> </tr> <tr> <th>Normal windows:</th> <td style="background-color:#F5EDD8">#F5EDD8</td> <td style="background-color:#101010">#101010</td> </tr> <tr> <th>Text windows:</th> <td style="background-color:#FFF">#FFF</td> <td style="background-color:#1A1A1A">#1A1A1A</td> </tr> <tr> <th>Selected items:</th> <td style="background-color:#F4C256">#F4C256</td> <td style="background-color:#1A1A1A">#1A1A1A</td> </tr> <tr> <th>Tooltips:</th> <td style="background-color:#F5F5B5">#F5F5B5</td> <td style="background-color:#000">#000</td> </tr> </table> <h2>Icon Theme</h2> <p>Download <a href="https://launchpad.net/~bisigi/+archive/ppa/+files/balanzan-theme_1.8.1.natty.ppa1.tar.gz">the whole package</a>, go to <code>balazan-theme/icons</code> and look into <code>balazan.tar.bz2</code>.</p> <p>Here are some of the icons:</p> <div style="width: 469px" class="wp-caption aligncenter"><a href="../images/2012/10/balazan-icons.png"><img src="../images/2012/10/balazan-icons.png" alt="Balanzan Icons" width="" height="" class="size-full wp-image-46541" /></a><p class="wp-caption-text">Balanzan Icons</p></div> <h2>Background</h2> <p>The background is based on “<a href="http://ubuntu.damianvila.com/">Lion Claar</a>” background by Damián Vila:</p> <div style="width: 160px" class="wp-caption alignright"><a href="../images/2012/10/balanzan_4_3-150x150.png"><img src="../images/2012/10/balanzan_4_3-150x150.png" alt="Balanzan 4:3 wallpaper" width="" height="" class="size-thumbnail wp-image-46491" /></a><p class="wp-caption-text">Balanzan 4:3 wallpaper</p></div> <div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2012/10/balanzan-150x150.png"><img src="../images/2012/10/balanzan-150x150.png" alt="Balanzan 16:9 wallpaper" width="" height="" class="size-thumbnail wp-image-46481" /></a><p class="wp-caption-text">Balanzan 16:9 wallpaper</p></div> PSE am KIT //martin-thoma.com/pse-am-kit/ Sun, 07 Oct 2012 16:09:59 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/pse-am-kit <p>Da es zum Modul „Praxis der Software-Entwicklung“ vom KIT leider nur verstreut Informationen gibt (die noch dazu teilweise veraltet sind) versuche ich mal für das Wintersemester 2012/2013 ein paar Informationen zu sammeln und darzustellen.</p> <h2>Allgemeines</h2> <ul> <li>max 10k LOC (Java / C++ / C#)</li> <li>2 `$\frac{\text{Tage}}{\text{Woche} \cdot \text{Teilnehmer}}$` sollte man einplanen (offiziell)</li> <li>Tools wollen sie sehen: Eclipse, GUI-Builder, JMetrics, Rational Architect, JCov</li> <li>Bis 18. November: Anmeldung in studium.kit.edu f&uuml;r PSE und Teamarbeit in der Software-Entwicklung</li> </ul> <h2>Modulhandbuch: PSE</h2> <p>Das Modul PSE wird als IN2INSWP bezeichnet und auf S. 37 beschrieben. Es findet <em>jedes Semester</em> statt und ist 6 ECTS-Punkte wert.</p> <h3>Erfolgskontrolle</h3> <blockquote>Die Erfolgskontrolle erfolgt nach &sect; 4 Abs. 2 Nr. 3 SPO als benotete Erfolgskontrolle anderer Art. Die in den Anmerkungen genannten Artefakte werden separat benotet und gehen mit folgendem Prozentsatz in die Gesamtnote ein: <ul> <li>Pflichtenheft 10%</li> <li>Entwurf 30%</li> <li>Implementierung 30%</li> <li>Qualit&auml;tssicherung 20%</li> <li>Abschlusspr&auml;sentation 10%</li> </ul></blockquote> <h3>Bedingungen</h3> <blockquote>Das Modul muss zusammen mit dem Modul Teamarbeit in der Software-Entwicklung [IN2INSWPS] belegt werden. Der erfolgreiche Abschluss der Module Grundbegriffe der Informatik [IN1INGI], Programmieren [IN1INPROG] und Softwaretechnik I [IN1INSWT1] wird vorausgesetzt.</blockquote> <h3>Lernziele</h3> <blockquote>Die Teilnehmer lernen, ein vollst&auml;ndiges Softwareprojekt nach dem Stand der Softwaretechnik in einem Team mit ca. 5-7 Teilnehmern durchzuf&uuml;hren. Ziel ist es insbesondere, Verfahren des Software-Entwurfs und der Qualit&auml;tssicherung praktisch einzusetzen, Implementierungskompetenz umzusetzen, und arbeitsteilig im Team zu kooperieren.</blockquote> <h3>Inhalt</h3> <blockquote><ul><li>Erstellung des Pflichtenheftes incl. Verwendungsszenarien</li> <li>Objektorientierter Entwurf nebst Feinspezifikation</li> <li>Implementierung in einer objektorientierten Sprache</li> <li>Funktionale Tests und &Uuml;berdeckungstests</li> <li>Einsatz von Werkzeugen (z.B. Eclipse, UML, Java, Junit, Jcov)</li> <li>Pr&auml;sentation des fertigen Systems</li></ul></blockquote> <h3>Anmerkungen</h3> <blockquote><strong>Zur Struktur</strong>: Das Praktikum gliedert sich in die Phasen Pflichtenheft, Entwurf und Feinspezifikation, Implementierung, Qualit&auml;tssicherung, Abschlusspr&auml;sentation. Alle Phasen werden nach dem Stand der Softwaretechnik objektorientiert und werkzeugunterst&uuml;tzt durchgef&uuml;hrt. Zu jeder Phase muss das entsprechende Artefakt (Pflichtenheft, UML-Diagramme mit Erl&auml;uterungen, vollst&auml;ndiger Java-Quellcode, Testprotokolle, laufendes System) in einem Kolloquium pr&auml;sentiert werden. Das vollst&auml;ndige System wird von den Betreuern auf Funktionalit&auml;t, Bedienbarkeit und Robustheit gepr&uuml;ft.</blockquote> <h2>Modulhandbuch: Teamarbeit in der Software-Entwicklung</h2> <p>Das Modul „Teamarbeit in der Software-Entwicklung“ wird als IN2INSWPS auf S. 39 des Modulhandbuchs beschrieben. Es ist 2 ECTS-Punkte wert und besteht aus nur einer Lehrveranstaltung (Teamarbeit und Präsentation in der Software-Entwicklung, S. 402)</p> <h3>Erfolgskontrolle</h3> <blockquote>Die Erfolgskontrolle erfolgt als benotete Erfolgskontrolle anderer Art nach &sect; 4 Abs. 2 Nr. 3 SPO. Teilnehmer m&uuml;ssen als Team von ca. 5 Studierenden Pr&auml;sentationen zu den Software-Entwicklungsphasen Pflichtenheft, Entwurf, Implementierung, Qualit&auml;tssicherung sowie eine Abschlusspr&auml;sentation von je 15 Minuten erarbeiten. Teilnehmer m&uuml;ssen Dokumente zur Projektplanung, insbesondere Qualit&auml;tssicherungsplan und Implementierungsplan vorlegen und umsetzen.</blockquote> <h3>Bedinungen</h3> <blockquote>Das Modul kann nur in Verbindung mit dem Modul Praxis der Software-Entwicklung [IN2INSWP] absolviert werden. Der erfolgreiche Abschluss der Module Grundbegriffe der Informatik [IN1INGI] und Programmieren [IN1INPROG] wird vorausgesetzt.</blockquote> <h3>Lernziele</h3> <blockquote>Die Teilnehmer erwerben wichtige nicht-technische Kompetenzen zur Durchf&uuml;hung von Softwareprojekten im Team. Dazu geh&ouml;ren Sprachkompetenz und kommunikative Kompetenz sowie Techniken der Teamarbeit, der Pr&auml;sentation und der Projektplanung.</blockquote> <h3>Inhalt</h3> <blockquote>Auseinandersetzung mit der Arbeit im Team, Kommunikations-, Organisations- und Konfliktbehandungsstrategien; Erarbeitung von Pr&auml;sentationen zu Pflichtenheft, Entwurf, Implementierung, Qualit&auml;tssicherung, Abschlusspr&auml;sentation; Projektplanungstechniken (z.B. Netzplantechnik, Phasenbeauftragte).</blockquote> <h3>Anmerkungen</h3> <blockquote>Dieses Modul erg&auml;nzt das Pflichtmodul Praxis der Software-Entwicklung [IN2INSWP]. Es ist ein Pflichtmodul. Studierende, die die Schl&uuml;sselqualifikationen bereits in vollem Umfang vorliegen, aber das Modul Praxis der Software-Entwicklung [IN2INSWP] noch nicht bestanden haben, kontaktieren bitte das Service-Zentrum Studium und Lehre.</blockquote> <h2>WebInscribe</h2> <p>Man meldet sich vermutlich bald unter <a href="https://webinscribe.ira.uka.de/pse2012">webinscribe.ira.uka.de/pse2012</a> an.</p> <h2>Termine</h2> <p><a href="http://pp.info.uni-karlsruhe.de/lehre/WS201213/pse/">Diese Seite</a> bietet ein paar weitere Informationen:</p> <p><strong>Auftaktveranstaltung</strong>: Montag, 15.10.2012 um 15:45 Uhr im Audimax <strong>Bis 18. November</strong>: Anmeldung in studium.kit.edu für PSE <strong>und</strong> Teamarbeit in der Software-Entwicklun</p> <h2>Themen</h2> <p>Sind unter „<a href="http://pp.info.uni-karlsruhe.de/lehre/WS201213/pse/">Aufgabenstellungen</a>“ zu finden und ein paar davon hier nochmals mit Links:</p> <table class="wikitable"> <tr> <th>&nbsp;</th> <th>Name</th> <th>Teams</th> <th>#, LV-Nr.</th> </tr> <tr> <td>TM <a href="http://www.cm-tm.uka.de/staff_abeck.php">Abeck</a></td> <td><a href="http://cm.tm.kit.edu/study_pse.php">CampusCoach - Entwicklung eines Web-basierten Coaching-Systems</a></td> <td>1</td> <td>1, 24041</td> </tr> <tr> <td>IFA <a href="http://wwwiaim.ira.uka.de/users/asfour/">Asfour</a></td> <td>Teleoperating eines humanoiden Roboters mit einem Android Tablet</td> <td>1</td> <td>#</td> </tr> <tr> <td>ITI Beckert</td> <td><a href="http://formal.iti.kit.edu/teaching/pse/2012/">Automatisches Pr&uuml;fen von Programmeigenschaften</a></td> <td>2</td> <td>#</td> </tr> <tr> <td><a href="http://pcs.tm.kit.edu/21_beigl.php">TM Beigl</a></td> <td><a href="http://pcs.tm.kit.edu/320_330.php">Point and Click - Steuerung von Intelligenten Umgebungen mit Android und Kinect</a></td> <td>4</td> <td>#</td> </tr> <tr> <td rowspan="2">IOSB Beyerer</td> <td>Steuerung mobiler Roboter im vermischten Windows-Linux Netzwerk &uuml;ber ROS-Middleware</td> <td>1</td> <td>#</td> </tr> <tr> <td>Multispektrale Datenbank</td> <td>1</td> <td>#</td> </tr> <tr> <td rowspan="3">IPD <a href="http://dbis.ipd.uni-karlsruhe.de/336.php">B&ouml;hm</a></td> <td><a href="http://dbis.ipd.uni-karlsruhe.de/1942.php">Ein lokaler Energiemarktplatz f&uuml;r das Smart Grid</a></td> <td>2</td> <td>#</td> </tr> <tr> <td>Management personenbezogener Daten in Crowdsourcing-Szenarien</td> <td>2</td> <td>#</td> </tr> <tr> <td>Generating Meaningful Statistics on Access Behavior to Scientific Data Bases</td> <td>2</td> <td>#</td> </tr> <tr> <td>IBDS <a href="http://cg.ibds.kit.edu/dachsbacher/index.php">Dachsbacher</a></td> <td><a href="http://cg.ibds.kit.edu/lehre/ws2012/pse/index.php">Echtzeitcomputergrafik in der Spieleentwicklung</a></td> <td>2</td> <td>#</td> </tr> <tr> <td><a href="http://dsn.tm.uni-karlsruhe.de/staff_hartenstein.php">TM Hartenstein</a></td> <td>Mein Fenster zur Welt &ndash; Visualisierung von Netzwerk-Traffic</td> <td>1</td> <td>#</td> </tr> <tr> <td>ITEC <a href="http://ces.itec.kit.edu/">Henkel</a></td> <td><a href="http://ces.itec.kit.edu/teaching/PSE_w1213/site_PSE.htm">Modulares Multimedia-Werkzeug zum Testen von Videoencodern</a></td> <td>2</td> <td>#</td> </tr> <tr> <td><a href="http://www.iks.kit.edu/index.php?id=iks-mueller-quade">IKS M&uuml;ller-Quade</a></td> <td><a href="https://www.iks.kit.edu/pse-ws12">Broadcast-Verschl&uuml;sselung &ndash; Pay-TV und andere Anwendungen</a></td> <td>1</td> <td>11</td> </tr> <tr> <td>IPD Reussner</td> <td><a href="https://sdqweb.ipd.kit.edu/wiki/Praxis_der_Software-Entwicklung_12_WS12/13">Bewertungssoftware f&uuml;r die Mensa</a></td> <td>4</td> <td>#</td> </tr> <tr> <td>IFA Schulz</td> <td>Tablet-basiertes Memory-Spiel f&uuml;r Menschen mit Demenz</td> <td>1</td> <td>#</td> </tr> <tr> <td rowspan="2">ITI Sanders</td> <td><a href="https://algo2.iti.kit.edu/2058.php">Entwicklung eines Routenplaners</a></td> <td>1</td> <td>#</td> </tr> <tr> <td>Flexibles Kartenrendering</td> <td>1</td> <td>#</td> </tr> <tr> <td><a href="http://www.ipd.kit.edu/Tichy/">IPD Tichy</a></td> <td>Der Microsoft Imagine Cup 2013 (<a href="http://en.wikipedia.org/wiki/Imagine_Cup">en-Wiki</a>)</td> <td>3</td> <td>#</td> </tr> </table> <p>30 Teams bei 5-7 Personen/Team <code>$\Rightarrow$</code> 150-210 Personen können dieses Semester PSE machen. Wir sind jedoch soweit ich weiß etwa 600…</p> Python Puzzle #3: Associativity //martin-thoma.com/python-puzzle-3-associativity/ Tue, 02 Oct 2012 21:31:50 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-puzzle-3-associativity <p>What is the output of</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="mi">1</span> <span class="ow">in</span> <span class="p">[]</span> <span class="ow">in</span> <span class="s">&#39;a&#39;</span></code></pre></div> <p>and what is the output of</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="p">(</span><span class="mi">1</span> <span class="ow">in</span> <span class="p">[])</span> <span class="ow">in</span> <span class="s">&#39;a&#39;</span></code></pre></div> <p>or</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="mi">1</span> <span class="ow">in</span> <span class="p">([]</span> <span class="ow">in</span> <span class="s">&#39;a&#39;</span><span class="p">)</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <p>The first expression evaluates to <code>False</code>, because it gets evaluated as <code>(1 in []) and ([] in 'a')</code> (<a href="http://docs.python.org/reference/expressions.html#not-in">Manual</a>, <a href="http://stackoverflow.com/a/12660938/562769">Source</a>).</p> <p>The second two expressions are invalid; they throw an error.</p> Sizes in LaTeX //martin-thoma.com/sizes-in-latex/ Sat, 29 Sep 2012 18:23:38 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sizes-in-latex <p>Here is an overview of sizes in LaTeX:</p> <h2>TikZ</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/09/tikz-sizes.png"><img src="../images/2012/09/tikz-sizes.png" alt="TikZ thicknes" width="" height="" class="size-full" /></a><p class="wp-caption-text">TikZ thicknes</p></div> <p>Usage example: <code>\draw[ultra thick, blue,dashed](a -| current plot begin) -- (a);</code></p> <ul> <li><code>ultra thin</code></li> <li><code>very thin</code></li> <li><code>thin</code></li> <li><code>semithick</code></li> <li><code>thick</code></li> <li><code>very thick</code></li> <li><code>ultra thick</code></li> </ul> <h2>Text</h2> <p style="text-align: center;"><a href="../images/2012/09/text-sizes-latex.png"><img class="size-full wp-image-45921 aligncenter" title="Text sizes in LaTeX" src="../images/2012/09/text-sizes-latex.png" alt="" width="512" height="110" /></a></p> <p>Usage example: <code>\Huge `$\varepsilon$`</code></p> <ul> <li><code>\tiny</code></li> <li><code>\scriptsize</code></li> <li><code>\footnotesize</code></li> <li><code>\small</code></li> <li><code>\normalsize</code></li> <li><code>\large</code></li> <li><code>\Large</code></li> <li><code>\LARGE</code></li> <li><code>\huge</code></li> <li><code>\Huge</code></li> </ul> <h2 id="math">Math</h2> <p>### Formulas</p> <div style="width: 319px" class="wp-caption aligncenter"><a href="../images/2012/09/latex-math-sizes.png"><img src="../images/2012/09/latex-math-sizes.png" alt="Sizes of different math modes" width="" height="" class="size-full wp-image-45931" /></a><p class="wp-caption-text">Sizes of different math modes</p></div> <p>Usage example: <code>`$\scriptstyle \lim_{n \rightarrow \infty} (1 + \frac{1}{n})^n$`</code></p> <ul> <li><code>\scriptscriptstyle</code></li> <li><code>\scriptstyle</code></li> <li><code>\textstyle</code></li> <li><code>\displaystyle</code></li> </ul> <h3 id="parentheses">Parentheses</h3> <p>The size of brackets <code>[ ]</code>, (curly) braces <code>{ }</code> and parentheses <code>( )</code> can be adjusted with these commands:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\[-1+x ( x \big( 1+ x\Big(2 + x \bigg(3+ x\Bigg(4+x \Bigg) \bigg) \Big) \big) )\] </pre></div> </div> </div> <p>The result will look like this</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/09/latex-parentheses-sizes.png"><img src="//martin-thoma.com/captions/latex-parentheses-sizes.png" alt="Sizes of parentheses" width="500" height="87" class="size-full" /></a><p class="wp-caption-text">Sizes of parentheses</p></div> Code golf //martin-thoma.com/code-golf/ Thu, 27 Sep 2012 08:47:50 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/code-golf <blockquote>Code golf is a type of recreational computer programming competition in which participants strive to achieve the shortest possible code that solves a certain problem.</blockquote> <p>Source: <a href="http://en.wikipedia.org/wiki/Code_golf">Wikipedia</a></p> <p>I’ve recently found some very interesting code golf examples on <a href="http://codegolf.stackexchange.com">codegolf.stackexchange.com</a>:</p> <h2>Snake</h2> <p><a href="http://codegolf.stackexchange.com/q/7241/5240">Task</a>: Recreate the classic snake Game.</p> <p>The shortest answer is written in <a href="http://codegolf.stackexchange.com/a/7260/5240">Ruby in 316 characters</a>, the longest is written in <a href="http://codegolf.stackexchange.com/a/7255/5240">Java in 2239 characters</a>.</p> <p>Here is a Python answer with 818 characters:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">import</span> <span class="nn">pygame</span> <span class="kn">as</span> <span class="nn">p</span> <span class="kn">from</span> <span class="nn">random</span> <span class="kn">import</span> <span class="n">randint</span> <span class="k">as</span> <span class="n">r</span> <span class="n">p</span><span class="o">.</span><span class="n">init</span><span class="p">();</span><span class="n">l</span><span class="o">=</span><span class="mi">20</span> <span class="n">c</span><span class="o">=</span><span class="n">p</span><span class="o">.</span><span class="n">time</span><span class="o">.</span><span class="n">Clock</span><span class="p">()</span> <span class="n">dp</span><span class="o">=</span><span class="n">p</span><span class="o">.</span><span class="n">display</span><span class="p">;</span><span class="n">w</span><span class="o">=</span><span class="n">p</span><span class="o">.</span><span class="n">display</span><span class="o">.</span><span class="n">set_mode</span><span class="p">((</span><span class="mi">500</span><span class="p">,</span><span class="mi">500</span><span class="p">))</span> <span class="n">C</span><span class="o">=</span><span class="n">p</span><span class="o">.</span><span class="n">Color</span><span class="p">;</span><span class="n">b</span><span class="o">=</span><span class="n">C</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">);</span><span class="n">g</span><span class="o">=</span><span class="n">C</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">255</span><span class="p">,</span><span class="mi">0</span><span class="p">)</span> <span class="n">D</span><span class="o">=</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">);</span><span class="n">U</span><span class="o">=</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">);</span><span class="n">L</span><span class="o">=</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">);</span><span class="n">R</span><span class="o">=</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">)</span> <span class="n">S</span><span class="o">=</span><span class="p">[</span><span class="n">R</span><span class="p">];</span><span class="n">d</span><span class="o">=</span><span class="n">R</span><span class="p">;</span><span class="n">n</span><span class="o">=</span><span class="p">[]</span> <span class="n">O</span><span class="o">=</span><span class="k">lambda</span> <span class="n">t</span><span class="p">:{</span><span class="n">U</span><span class="p">:</span><span class="n">D</span><span class="p">,</span><span class="n">R</span><span class="p">:</span><span class="n">L</span><span class="p">,</span><span class="n">D</span><span class="p">:</span><span class="n">U</span><span class="p">,</span><span class="n">L</span><span class="p">:</span><span class="n">R</span><span class="p">}[</span><span class="n">t</span><span class="p">]</span> <span class="k">def</span> <span class="nf">Q</span><span class="p">(</span><span class="n">e</span><span class="p">):</span><span class="k">print</span> <span class="s">&quot;Score: </span><span class="si">%i</span><span class="s">&quot;</span><span class="o">%</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="n">S</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span><span class="p">);</span><span class="n">p</span><span class="o">.</span><span class="n">quit</span><span class="p">()</span> <span class="k">def</span> <span class="nf">K</span><span class="p">(</span><span class="n">e</span><span class="p">):</span><span class="k">global</span> <span class="n">d</span><span class="p">;</span><span class="n">_</span><span class="o">=</span><span class="p">{</span><span class="mi">276</span><span class="p">:</span><span class="n">L</span><span class="p">,</span><span class="mi">273</span><span class="p">:</span><span class="n">U</span><span class="p">,</span><span class="mi">274</span><span class="p">:</span><span class="n">D</span><span class="p">,</span><span class="mi">275</span><span class="p">:</span><span class="n">R</span><span class="p">}</span><span class="o">.</span><span class="n">get</span><span class="p">(</span><span class="n">e</span><span class="o">.</span><span class="n">key</span><span class="p">,(</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">));</span><span class="n">d</span><span class="o">=</span><span class="ow">not</span> <span class="n">_</span><span class="o">==</span><span class="n">O</span><span class="p">(</span><span class="n">d</span><span class="p">)</span> <span class="ow">and</span> <span class="n">_</span> <span class="ow">or</span> <span class="n">d</span> <span class="k">def</span> <span class="nf">N</span><span class="p">(</span><span class="n">S</span><span class="p">):[</span><span class="n">p</span><span class="o">.</span><span class="n">draw</span><span class="o">.</span><span class="n">rect</span><span class="p">(</span><span class="n">w</span><span class="p">,</span><span class="n">g</span><span class="p">,[</span><span class="n">x</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span><span class="o">*</span><span class="n">l</span><span class="p">,</span><span class="n">x</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span><span class="o">*</span><span class="n">l</span><span class="p">,</span><span class="n">l</span><span class="p">,</span><span class="n">l</span><span class="p">])</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">S</span><span class="o">+</span><span class="n">n</span><span class="p">]</span> <span class="k">def</span> <span class="nf">M</span><span class="p">():</span><span class="n">n</span><span class="o">=</span><span class="p">(</span><span class="n">r</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">24</span><span class="p">),</span><span class="n">r</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="mi">24</span><span class="p">));</span><span class="k">return</span> <span class="n">n</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">S</span> <span class="ow">and</span> <span class="n">n</span> <span class="ow">or</span> <span class="n">M</span><span class="p">()</span> <span class="n">A</span><span class="o">=</span><span class="k">lambda</span> <span class="n">s</span><span class="p">,</span><span class="n">o</span><span class="p">:</span><span class="nb">tuple</span><span class="p">(</span><span class="n">x</span><span class="o">+</span><span class="n">y</span> <span class="k">for</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span> <span class="ow">in</span> <span class="nb">zip</span><span class="p">(</span><span class="n">s</span><span class="p">,</span><span class="n">o</span><span class="p">))</span> <span class="n">n</span><span class="o">=</span><span class="p">[</span><span class="n">M</span><span class="p">()]</span> <span class="k">while</span> <span class="bp">True</span><span class="p">:</span> <span class="n">w</span><span class="o">.</span><span class="n">fill</span><span class="p">(</span><span class="n">b</span><span class="p">);[{</span><span class="mi">12</span><span class="p">:</span><span class="n">Q</span><span class="p">,</span><span class="mi">2</span><span class="p">:</span><span class="n">K</span><span class="p">}</span><span class="o">.</span><span class="n">get</span><span class="p">(</span><span class="n">e</span><span class="o">.</span><span class="n">type</span><span class="p">,</span><span class="k">lambda</span> <span class="n">e</span><span class="p">:</span><span class="n">e</span><span class="p">)(</span><span class="n">e</span><span class="p">)</span> <span class="k">for</span> <span class="n">e</span> <span class="ow">in</span> <span class="n">p</span><span class="o">.</span><span class="n">event</span><span class="o">.</span><span class="n">get</span><span class="p">()]</span> <span class="k">if</span> <span class="ow">not</span> <span class="p">(</span><span class="mi">0</span><span class="o">&lt;=</span><span class="n">S</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span><span class="o">&lt;</span><span class="mi">25</span> <span class="ow">and</span> <span class="mi">0</span><span class="o">&lt;=</span><span class="n">S</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">][</span><span class="mi">1</span><span class="p">]</span><span class="o">&lt;</span><span class="mi">25</span><span class="p">)</span> <span class="ow">or</span> <span class="n">A</span><span class="p">(</span><span class="n">S</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span><span class="n">d</span><span class="p">)</span> <span class="ow">in</span> <span class="n">S</span><span class="p">:</span> <span class="n">Q</span><span class="p">(</span><span class="n">e</span><span class="p">)</span> <span class="k">if</span> <span class="n">A</span><span class="p">(</span><span class="n">S</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span><span class="n">d</span><span class="p">)</span> <span class="ow">in</span> <span class="n">n</span><span class="p">:</span> <span class="n">S</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">A</span><span class="p">(</span><span class="n">S</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span><span class="n">d</span><span class="p">));</span><span class="n">n</span><span class="o">=</span><span class="p">[</span><span class="n">M</span><span class="p">()]</span> <span class="k">else</span><span class="p">:</span> <span class="n">S</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">A</span><span class="p">(</span><span class="n">S</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span><span class="n">d</span><span class="p">));</span><span class="n">S</span><span class="o">.</span><span class="n">pop</span><span class="p">(</span><span class="mi">0</span><span class="p">)</span> <span class="n">N</span><span class="p">(</span><span class="n">S</span><span class="p">);</span><span class="n">dp</span><span class="o">.</span><span class="n">update</span><span class="p">();</span><span class="n">c</span><span class="o">.</span><span class="n">tick</span><span class="p">(</span><span class="mi">6</span><span class="p">)</span></code></pre></div> <h2>Matrix determinant</h2> <p><a href="http://codegolf.stackexchange.com/q/8405/5240">Task</a>: Calculate the determinant of a <code>$n \times n$</code> matrix.</p> <p>Solution in <a href="http://en.wikipedia.org/wiki/J_(programming_language)">J</a> (61 characters):</p> <div class="highlight"><pre><code class="language-text" data-lang="text">-/&gt;([:+/#(([{.&lt;:@[}.])[:*//._2,\2#])])&amp;amp;.&gt;(|.;])&quot;.];._2[1!:1[3</code></pre></div> <p>Solution in Python (198 characters):</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">t</span><span class="o">=</span><span class="nb">input</span><span class="p">()</span> <span class="n">e</span><span class="o">=</span><span class="nb">enumerate</span> <span class="n">p</span><span class="o">=</span><span class="k">lambda</span> <span class="n">t</span><span class="p">:</span><span class="n">t</span> <span class="ow">and</span><span class="p">((</span><span class="n">b</span><span class="o">+</span><span class="p">[</span><span class="n">a</span><span class="p">],</span><span class="n">j</span><span class="o">+</span><span class="n">i</span><span class="p">)</span><span class="k">for</span> <span class="n">i</span><span class="p">,</span><span class="n">a</span> <span class="ow">in</span> <span class="n">e</span><span class="p">(</span><span class="n">t</span><span class="p">)</span><span class="k">for</span> <span class="n">b</span><span class="p">,</span><span class="n">j</span> <span class="ow">in</span> <span class="n">p</span><span class="p">(</span><span class="n">t</span><span class="p">[:</span><span class="n">i</span><span class="p">]</span><span class="o">+</span><span class="n">t</span><span class="p">[</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">:]))</span><span class="ow">or</span><span class="p">[([],</span><span class="mi">0</span><span class="p">)]</span> <span class="k">print</span> <span class="nb">sum</span><span class="p">(</span><span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">t</span><span class="p">,(</span><span class="n">i</span><span class="p">,</span><span class="n">r</span><span class="p">):</span><span class="n">t</span><span class="o">*</span><span class="n">r</span><span class="p">[</span><span class="n">i</span><span class="p">],</span><span class="n">e</span><span class="p">(</span><span class="n">p</span><span class="p">),</span><span class="mi">1</span><span class="o">-</span><span class="n">i</span><span class="o">%</span><span class="mi">2</span><span class="o">*</span><span class="mi">2</span><span class="p">)</span><span class="k">for</span> <span class="n">p</span><span class="p">,</span><span class="n">i</span> <span class="ow">in</span> <span class="n">p</span><span class="p">([</span><span class="n">t</span><span class="p">]</span><span class="o">+</span><span class="p">[</span><span class="nb">input</span><span class="p">()</span><span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">:]]))</span></code></pre></div> <h2>Factorial</h2> <p><a href="http://codegolf.stackexchange.com/q/607/5240">Task</a>: Find the factorial of a number.</p> <p>J (12 characters):</p> <div class="highlight"><pre><code class="language-text" data-lang="text">f=:*/@:&gt;:@i.</code></pre></div> <p>Python (27 characters):</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">f</span><span class="o">=</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span><span class="mi">0</span><span class="o">**</span><span class="n">x</span> <span class="ow">or</span> <span class="n">x</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">x</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span></code></pre></div> <p>By the way, the shortest Java solution is 85 characters long^^.</p> Crash Course: World History //martin-thoma.com/crash-course-world-history/ Fri, 21 Sep 2012 19:19:52 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/crash-course-world-history <h2>#32: Coal, Steam, and The Industrial Revolution</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/zhL5DCizj5c" frameborder="0" allowfullscreen=""></iframe> <h2>A list</h2> <p>Here is the <a href="http://www.youtube.com/course?list=ECBDA2E52FB1EF80C9">YouTube Playlist</a>:</p> <ul> <li>#1: <a href="http://www.youtube.com/watch?v=Yocja_N5s1I">The Agricultural Revolution</a></li> <li>#2: <a href="http://www.youtube.com/watch?v=n7ndRwqJYDM">Indus Valley Civilization</a> - <a href="http://en.wikipedia.org/wiki/Indus_Valley_Civilization">Wikipedia</a></li> <li>#3: <a href="http://www.youtube.com/watch?v=sohXPx_XZ6Y">Mesopotamia</a></li> <li>#4: <a href="http://www.youtube.com/watch?v=Z3Wvw6BivVI">Ancient Egypt</a></li> <li>#5: <a href="http://www.youtube.com/watch?v=Q-mkVSasZIM">The Persians &amp; Greeks</a></li> <li>#6: <a href="http://www.youtube.com/watch?v=8Nn5uqE3C9w">Buddha and Ashoka</a></li> <li>#7: <a href="http://www.youtube.com/watch?v=ylWORyToTo4">&lrm;2,000 Years of Chinese History! The Mandate of Heaven and Confucius</a></li> <li>#8: <a href="http://www.youtube.com/watch?v=0LsrkWDCvxg">Alexander the Great and the Situation ... the Great?</a></li> <li>#9: <a href="http://www.youtube.com/watch?v=vfe-eNq-Qyg">The Silk Road and Ancient Trade</a></li> <li>#10: <a href="http://www.youtube.com/watch?v=oPf27gAup9U">The Roman Empire. Or Republic. Or...Which Was It?</a></li> <li>#11: <a href="http://www.youtube.com/watch?v=TG55ErfdaeY">Christianity from Judaism to the Constantine</a></li> <li>#12: <a href="http://www.youtube.com/watch?v=3PszVWZNWVA">Fall of The Roman Empire...in the 15th Century</a></li> <li>#13: <a href="http://www.youtube.com/watch?v=TpcbfxtdoI8">Islam, the Quran, and the Five Pillars All Without a Flamewar</a></li> <li>#14: <a href="http://www.youtube.com/watch?v=QV7CanyzhZg">The Dark Ages...How Dark Were They, Really?</a></li> <li>#15: <a href="http://www.youtube.com/watch?v=X0zudTQelzI">The Crusades - Pilgrimage or Holy War?</a></li> <li>#16: <a href="http://www.youtube.com/watch?v=jvnU0v6hcUo">Mansa Musa and Islam in Africa</a></li> <li>#17: <a href="http://www.youtube.com/watch?v=szxPar0BcMo">Wait For It...The Mongols!</a></li> <li>#18: <a href="http://www.youtube.com/watch?v=a6XtBLDmPA0">International Commerce, Snorkeling Camels, and The Indian Ocean Trade</a></li> <li>#19: <a href="http://www.youtube.com/watch?v=UN-II_jBzzo">Venice and the Ottoman Empire</a></li> <li>#20: <a href="http://www.youtube.com/watch?v=etmRI2_9Q_A">Russia, the Kievan Rus, and the Mongols</a></li> <li>#21: <a href="http://www.youtube.com/watch?v=NjEGncridoQ">Columbus, de Gama, and Zheng He! 15th Century Mariners</a></li> <li>#22: <a href="http://www.youtube.com/watch?v=Vufba_ZcoR0">The Renaissance: Was it a Thing?</a></li> <li>#23: <a href="http://www.youtube.com/watch?v=HQPA5oNpfM4">The Columbian Exchange</a></li> <li>#24: <a href="http://www.youtube.com/watch?v=dnV_MTFEGIY">The Atlantic Slave Trade</a></li> <li>#25: <a href="http://www.youtube.com/watch?v=rjhIzemLdos">The Spanish Empire, Silver, &amp; Runaway Inflation</a></li> <li>#26: <a href="http://www.youtube.com/watch?v=j0qbzNHmfW0">The Seven Years War</a></li> <li>#27: <a href="http://www.youtube.com/watch?v=2yXNrLTddME">The Amazing Life and Strange Death of Captain Cook</a></li> <li>#28: <a href="http://www.youtube.com/watch?v=HlUiSBXQHCw">Tea, Taxes, and The American Revolution</a></li> <li>#29: <a href="http://www.youtube.com/watch?v=lTTvKwCylFY">The French Revolution</a></li> <li>#30: <a href="http://www.youtube.com/watch?v=5A_o-nU5s2U">Haitian Revolutions</a></li> <li>#31: <a href="http://www.youtube.com/watch?v=ZBw35Ze3bg8">Latin American Revolutions</a></li> <li>#32: <a href="http://www.youtube.com/watch?v=zhL5DCizj5c">Coal, Steam, and The Industrial Revolution</a></li> <li>#33: <a href="http://www.youtube.com/watch?v=B3u4EFTwprM">Capitalism and Socialism</a></li> <li>#34: <a href="http://www.youtube.com/watch?v=Nosq94oCl_M">Samurai, Daimyo, Matthew Perry, and Nationalism</a></li> <li>#35: <a href="http://www.youtube.com/watch?v=alJaltUmrGo">Imperialism</a></li> <li>#36: <a href="http://www.youtube.com/watch?v=_XPZQ0LAlR4">Archdukes, Cynicism, and World War I</a></li> </ul> Aufgaben zur Integralrechnung //martin-thoma.com/aufgaben-zur-integralrechnung/ Thu, 20 Sep 2012 08:56:07 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/aufgaben-zur-integralrechnung <p>Hier sind ein paar schöne Aufgaben und ausführliche Lösungsfindungsbeschreibungen zur Integralrechnung.</p> <p>Diesen Artikel werde ich ergänzen, wenn ich weitere schöne Aufgaben finde.</p> <h2>Aufgabe 1</h2> <p><strong>Aufgabenstellung</strong>:</p> <p>Berechne das bestimmte Integral <code>$\int_1^2 \frac{\arctan(x)}{x^2} dx$</code>.</p> <p><strong>Wissen</strong>:</p> <ul> <li>Partielle Integration</li> <li>Integration durch Substitution</li> <li>Partialbruchzerlegung</li> <li>`$(\arctan(x))' = \frac{1}{1+x^2}$`</li> <li>`$\arctan(1) = \frac{1}{4}$`</li> </ul> <p><strong>Rechnung</strong>:</p> <p>Partielle Integration mit:</p> <ul> <li>`$f(x) = \arctan(x) \rightarrow f'(x) = \frac{1}{1+x^2}$`</li> <li>`$g'(x)= x^{-2} \rightarrow g(x) = -x^{-1}$`</li> </ul> <p><code>$ \begin{align} \int_1^2 \frac{\arctan(x)}{x^2} dx &amp;= \left [ \arctan(x) \cdot (- \frac{1}{x}) \right ]_1^2 - \int_1^2 \frac{-1}{x \cdot (1+x^2)} dx\\ &amp;= - \frac{1}{2} \arctan(2) + \underbrace{\arctan(1)}_{\frac{1}{4}} + \int_1^2 \frac{1}{x \cdot (1+x^2)} dx \end{align}$</code></p> <p>Partialbruchzerlegung mit: <code>$\frac{A}{x} + \frac{B}{1+x^2} = \frac{1}{x \cdot (1+x^2)}\\ \Leftrightarrow A \cdot (1+x^2) + B \cdot x = 1\\ \Leftrightarrow A + Bx + Ax^2 = 1\\ \Rightarrow A= 1 \land B = -x:\\ \frac{1}{x} + \frac{-x}{1+x^2} = \frac{1}{x \cdot (1+x^2)}$</code></p> <p><code>$\begin{align} \int_1^2 \frac{\arctan(x)}{x^2} dx &amp;= \frac{1}{4} - \frac{1}{2} \arctan(2) + \int_1^2 \frac{1}{x} dx - \int_1^2 \frac{x}{1+x^2} dx\\ \end{align}$</code></p> <p>Substitution mit:</p> <ul> <li>`$u := 1+x^2$`</li> <li>`$\frac{du}{dx} = u' = 2x \rightarrow dx = \frac{du}{2x}$`</li> </ul> <p><code>$\begin{align} \int_1^2 \frac{\arctan(x)}{x^2} dx &amp;= \frac{1}{4} - \frac{1}{2} \arctan(2) + \left [ \log x \right ]_1^2 - \int_2^5 \frac{1}{2u} du\\ &amp;= \frac{1}{4} - \frac{1}{2} \arctan(2) + \log 2 - \frac{1}{2} \int_2^5 x dx\\ &amp;= \frac{1}{4} - \frac{1}{2} \arctan(2) + \log 2 - \frac{1}{2} \left [ \log(x) \right ]_2^5\\ &amp;= \frac{1}{4} - \frac{1}{2} \arctan(2) + \log 2 - \frac{1}{2} \log 5 + \frac{1}{2} \log 2\\ &amp;= \frac{1}{4} - \frac{1}{2} \arctan(2) + \frac{3}{2} \log 2 - \frac{1}{2} \log 5\\ &amp;= \frac{1}{2} \cdot \left (\frac{1}{2} - \arctan(2) + 3 \log 2 - \log 5 \right ) \end{align}$</code></p> <p><strong>Kontrolle</strong>: <a href="http://www.wolframalpha.com/input/?i=int+arctan%28x%29%2Fx%5E2+dx">Wolfram|Alpha</a></p> <h2>Aufgabe 2</h2> <p>Diese Aufgabe war in der Analysis I-Klausur vom Herbst 2006 am KIT. <strong>Aufgabenstellung</strong>:</p> <p>Berechne das bestimmte Integral <code>$\displaystyle \int_0^1 \frac{1}{(\sqrt[3]{x}+2) \cdot (\sqrt[3]{x}+1)} dx$</code>.</p> <p><strong>Wissen</strong>:</p> <ul> <li>Integration durch Substitution</li> <li>Partialbruchzerlegung</li> <li>Logarithmusgesetze</li> </ul> <p><strong>Rechnung</strong>: Kommt vielleicht später noch.</p> Integration durch Substitution //martin-thoma.com/integration-durch-substitution/ Sun, 16 Sep 2012 11:32:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/integration-durch-substitution <p>Integration durch Substitution ist eine elementare Methode zum finden von Stammfunktionen von Integralen bzw. zum berechnen von Integralen.</p> <h2>Unbestimmte Integrale</h2> <h3>Beispiel 1</h3> <p><code>$\int e^{2x} dx = ?$</code></p> <p>Substituiere <code>$u = 2x$</code> und <code>$u'(x) = \frac{du}{dx} = 2 \Rightarrow dx = \frac{du}{2}$</code> Also: <code>$\begin{align} \int e^{2x} dx &amp;\stackrel{sub}{=}\\ &amp;= \int e^u \frac{du}{2}\\ &amp;= \int \frac{1}{2} e^u du\\ &amp;= \frac{1}{2} \int e^u du\\ &amp;= \frac{1}{2} \int e^u du\\ &amp;= \frac{1}{2} e^u + C \\ &amp;\stackrel{resub}{=} \frac{1}{2} e^{2x} + C \end{align}$</code></p> <h3>Beispiel 2</h3> <p><code>$\int (x-1)^2 dx = ?$</code></p> <p>Substituiere <code>$u = x-1$</code> und <code>$u'(x) = \frac{ \;\mathrm{d}u}{dx} 1 \Rightarrow dx = \;\mathrm{d}u$</code> Also: <code>$\begin{align} \int (x-1)^2 dx &amp;\stackrel{sub}{=}\\ &amp;= \int u^2 \;\mathrm{d}u\\ &amp;= \frac{1}{3} u^3 + C &amp;\stackrel{resub}{=} \frac{1}{3} (x-1)^3 + C \end{align}$</code></p> <h2>Bestimmte Integrale</h2> <p>Bei bestimmten Integralen muss man die Grenzen auch ersetzen.</p> <h3>Beispiel 1</h3> <p>Dieses Beispiel stammt aus der Klausur „Analysis I“ vom Herbst 2010.</p> <p>Berechne <code>$\int_1^4 e^{\sqrt{x}} dx$</code>.</p> <p>Substituiere: <code>$\begin{align} u &amp;= \sqrt x\\ \frac{\;\mathrm{d}u}{dx} &amp;= u' = \frac{1}{2\sqrt{x}}\\ \Leftrightarrow dx &amp;= 2 \sqrt{x} \;\mathrm{d}u = 2 u \;\mathrm{d}u \end{align}$</code>.</p> <p>Es gilt: <code>$\int_1^4 e^{\sqrt{x}} dx = \int_1^2 e^u 2 u \;\mathrm{d}u = 2 \int_1^2 u \cdot e^u \;\mathrm{d}u$</code>.</p> <p>Nun wird eine <a href="../partielle-integration/" title="Partielle Integration">partielle Integration</a> durchgeführt mit <code>$f'(u)=e^u$</code> und <code>$g(u)=u$</code>:</p> <p><code>$\begin{align} 2 \int_1^2 u \cdot e^u \;\mathrm{d}u &amp;= 2 ([e^u \cdot u]_1^2 - \int_1^2 e^u du) \\ &amp;= 2((e^2 \cdot 2 - e) - [e^u]_1^2)\\ &amp;= 2 \cdot (2e^2 -e - (e^2 - e)) \\ &amp;= 2 \cdot e^2 \end{align}$</code></p> Partielle Integration //martin-thoma.com/partielle-integration/ Sat, 15 Sep 2012 19:02:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/partielle-integration <p>Die partielle Integration bietet eine schöne Möglichkeit, Stammfunktionen von Integralen zu bestimmen. Dazu muss man folgende Regel können:</p> <p>Seien <code>$f, g$</code> stetig differenzierbare Funktionen.</p> <p><code>$\displaystyle \int_a^b f'(x)\cdot g(x)\,\mathrm{d}x = \left [f(x)\cdot g(x) \right ]_{a}^{b} - \int_a^b f(x)\cdot g'(x)\,\mathrm{d}x$</code>.</p> <h2>Beispiel</h2> <p>Folgendes <a href="http://de.wikipedia.org/wiki/Partielle_Integration#Beispiel_1">Beispiel aus Wikipedia</a> zeigt, wie man das geschickt nutzen kann:</p> <p><strong>Aufgabe</strong>: Berechne <code>$\int \sin(x) \cdot \cos(x) \,\mathrm{d}x$</code></p> <p><strong>Lösung</strong>: Es sei <code>$f(x) = \cos(x)$</code> und <code>$g'(x)= \sin(x)$</code>. Es gilt: <code>$f'(x) = - \sin(x)$</code> und <code>$g(x)= - \cos(x)$</code>.</p> <p>Durch partielle Integration erhält man: <code>$\int \sin(x) \cdot \cos(x) \,\mathrm{d}x = -\cos^2(x) - \int \sin(x) \cdot \cos(x) \,\mathrm{d}x. $</code></p> <p>Addiert man auf beiden Seiten der Gleichung das Ausgangsintegral, ergibt sich: <code>$\begin{align} 2 \int \sin(x) \cdot \cos(x) \,\mathrm{d}x &amp;= - \cos^2(x)\\ \Leftrightarrow \int \sin(x) \cdot \cos(x) \,\mathrm{d}x &amp;= -\tfrac12\cos^2(x) \end{align}$</code></p> Konvergenz von Reihen //martin-thoma.com/konvergenz-von-reihen/ Sat, 15 Sep 2012 09:02:02 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/konvergenz-von-reihen <p>Die folgenden Definitionen sind wortwörtlich aus dem <a href="http://mitschriebwiki.nomeata.de/Ana1.pdf">inoffiziellem Skript für Analysis I</a> bei Herrn Dr. Schmoeger übernommen worden.</p> <h2>Dreiecksungleichung</h2> <div class="definition">Ist `$\sum_{n=1}^{\infty}a_n$` absolut konvergent, so ist `$\sum_{n=1}^{\infty}a_n$` konvergent und es gilt: `$\left | \sum_{n=1}^{\infty}a_n \right | \leq \sum_{n=1}^{\infty} |a_n|$`</div> <h2>Leibniz-Kriterium</h2> <div class="definition">Sei `$(a_n)_{n \in \mathbb{N}}$` eine monoton fallende, reelle Nullfolge. Dann konvergiert die alternierende Reihe `$s = \sum_{n=0}^\infty (-1)^n a_n$`.</div> <h2>Wurzelkriterium</h2> <div class="definition">Sei `$(a_n)$` eine Folge und `$\alpha := \lim \sup \sqrt[n]{|a_n|}$`. <ol> <li>`$\alpha &lt; 1 \Rightarrow \sum_{n=1}^{\infty} a_n$` konvergiert absolut</li> <li>`$\alpha &gt; 1 \Rightarrow \sum_{n=1}^{\infty} a_n$` divergiert</li> <li>`$\alpha = 1 \Rightarrow$` keine Aussage &uuml;ber die Konvergenz von `$\sum_{n=1}^{\infty} a_n$` m&ouml;glich</li> </ol> </div> <h2>Majorantenkriterium</h2> <div class="definition">Gilt `$|a_n| \leq b_n ~\text{ffa } n \in \mathbb{N}$` und ist `$\sum_{n=1}^{\infty} b_n$` konvergent, so gilt: `$\sum_{n=1}^{\infty} a_n$` ist absolut konvergent.</div> <h2>Minorantenkriterium</h2> <div class="definition">Gilt `$a_n \geq b_n \geq 0 ~\text{ffa } n \in \mathbb{N}$` und ist `$\sum_{n=1}^{\infty} b_n$` divergent, so gilt: `$\sum_{n=1}^{\infty} a_n$` ist divergent.</div> <h2>Quotientenkriterium</h2> <div class="definition">Sei `$(a_n)$` eine Folge in `$\mathbb{R}$` und `$a_n \ne 0 \text{ ffa } \mathbb{N}$`. `$\alpha_n := \frac{a_{n+1}}{a_n}$` (ffa `$n \in \mathbb{N}$`). <ul> <li>Ist `$|\alpha_n| \ge 1 \text{ ffa } n \in \mathbb{N} \Rightarrow \sum a_n$` ist divergent.</li> <li>Es sei `$(\alpha_n)$` beschr&auml;nkt, `$\beta := \liminf |\alpha_n|$` und `$\alpha := \limsup |\alpha_n|$`.</li> <ul> <li>Ist `$\beta &gt; 1 \Rightarrow \sum a_n$` ist divergent.</li> <li>Ist `$\alpha &lt; 1 \Rightarrow \sum a_n$` ist absolut konvergent.</li> <li>Ist `$\alpha = \beta = 1$`, so ist keine allgemeine Aussage m&ouml;glich.</li> </ul> </ul></div> Neil deGrasse Tyson //martin-thoma.com/neil-degrasse-tyson/ Fri, 14 Sep 2012 18:26:00 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/neil-degrasse-tyson <div style="width: 138px" class="wp-caption alignright"><a href="../images/2012/09/Neil_deGrasse_Tyson.jpg"><img src="../images/2012/09/Neil_deGrasse_Tyson.jpg" alt="Neil deGrasse Tyson" width="" height="" class="size-full wp-image-44861" /></a><p class="wp-caption-text">Neil deGrasse Tyson</p></div> <p><a href="http://en.wikipedia.org/wiki/Neil_degrasse">Neil deGrasse Tyson</a> is an American astrophysicist and science communicator. He is currently the Frederick P. Rose Director of the Hayden Planetarium at the Rose Center for Earth and Space and a research associate in the department of astrophysics at the American Museum of Natural History. And he gives hilarious talks and interviews.</p> <h2>Death By Black Hole</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/h1iJXOUMJpg" frameborder="0" allowfullscreen=""></iframe> <h2>Death By Giant Meteor</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/xaW4Ol3_M1o" frameborder="0" allowfullscreen=""></iframe> <p><a href="http://en.wikipedia.org/wiki/99942_Apophis">Apophis</a> is a near-Earth asteroid that caused a brief period of concern in December 2004 because initial observations indicated a small probability (up to 2.7%) that it would strike the Earth in 2029.</p> <h2>How to Deflect a Killer Asteroid</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/1-ReuLZ2quc" frameborder="0" allowfullscreen=""></iframe> <h2>Earth Is Bad for Life</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/GgGgkkGE7QU" frameborder="0" allowfullscreen=""></iframe> <h2>My Man, Sir Isaac Newton</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/danYFxGnFxQ" frameborder="0" allowfullscreen=""></iframe> Jordansche Normalform: 4x4 Matrizen //martin-thoma.com/jordansche-normalform-4x4-matrizen/ Mon, 10 Sep 2012 11:28:08 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/jordansche-normalform-4x4-matrizen <div class="info">Hier sind `$4 \times 4$` Beispiele zum Hauptartikel <a href="../wie-berechnet-man-die-jordansche-normalform/" title="Wie berechnet man die Jordan&rsquo;sche Normalform?">Wie berechnet man die Jordan&rsquo;sche Normalform?</a>.</div> <h2>Beispiel 1</h2> <p>Gegeben sei die Matrix <code>$A \in \mathbb{R}^{4 \times 4}$</code>: <code>$A := \begin{pmatrix} 1 &amp; 2 &amp; 47 &amp; 11\\ 3 &amp; 2 &amp; 8 &amp; 15\\ 0 &amp; 0 &amp; 3 &amp; 1\\ 0 &amp; 0 &amp; 8 &amp; 1 \end{pmatrix}$</code>.</p> <h3>Jordannormalform bestimmen</h3> <p><strong>1. Charakteristisches Polynom berechnen:</strong> <code>$p_A(\lambda) = (\lambda - 5) \cdot (\lambda - 4) \cdot (\lambda + 1)^2$</code>.</p> <p>(→ <a href="http://www.wolframalpha.com/input/?i=%7B%7B1%2C2%2C47%2C11%7D%2C%7B3%2C2%2C8%2C15%7D%2C%7B0%2C0%2C3%2C1%7D%2C%7B0%2C0%2C8%2C1%7D%7D">Wolfram|Alpha</a> und „<a href="../wie-berechnet-man-das-charakteristische-polynom/">Wie berechnet man das charakteristische Polynom?</a>“)</p> <p>Daraus folgt:</p> <ul> <li>`$\lambda = 5$` ist Eigenwert mit der algebraischen Vielfachheit 1.</li> <li>`$\lambda = 4$` ist Eigenwert mit der algebraischen Vielfachheit 1.</li> <li>`$\lambda = -1$` ist Eigenwert mit der algebraischen Vielfachheit 2.</li> </ul> <p>Es gibt also genau drei Jordan-Blöcke in der Jordannormalform. Zwei davon haben die Kantenlänge 1 und deshalb nur ein Jordan-Kästchen.</p> <p><strong>2. Anzahl der Jordankästchen bestimmen:</strong></p> <p><code>$ \begin{align} \dim \text{Eig}(-1) &amp;= \dim \text{Kern}(A +1 \cdot I) \\ &amp;= \dim \text{Kern} \begin{pmatrix} 2 &amp; 2 &amp; 47 &amp; 11\\ 3 &amp; 3 &amp; 8 &amp; 15\\ 0 &amp; 0 &amp; 4 &amp; 1\\ 0 &amp; 0 &amp; 8 &amp; 2 \end{pmatrix}\\ &amp;= \dim \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 1.5 &amp; 0\\ 1 &amp; 1 &amp; -3 &amp; 13\\ 0 &amp; 0 &amp; 1 &amp; \frac{1}{4}\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix}\\ &amp;= \dim \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 1.5 &amp; 0\\ 0 &amp; 0 &amp; -4.5 &amp; 13\\ 0 &amp; 0 &amp; 1 &amp; \frac{1}{4}\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix}\\ &amp;= \dim \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 1.5 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 14 \frac{1}{8}\\ 0 &amp; 0 &amp; 1 &amp; \frac{1}{4}\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix}\\ &amp;= \dim \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 1 \end{pmatrix} = \dim \left [ \begin{pmatrix}1\\-1\\0\\0 \end{pmatrix}\right ]\\ &amp;= 1 \end{align} $</code></p> <p>Es gibt im Jordanblock zu <code>$\lambda = -1$</code> also genau ein Jordankästchen.</p> <p>Also ist die Jordansche Normalform festgelegt:</p> <p><code>$J_A = \begin{pmatrix} -1 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 4 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 5 \end{pmatrix}$</code></p> <p><a href="http://www.wolframalpha.com/input/?i=%7B%7B1%2C2%2C47%2C11%7D%2C%7B3%2C2%2C8%2C15%7D%2C%7B0%2C0%2C3%2C1%7D%2C%7B0%2C0%2C8%2C1%7D%7D">Kontrolle mit Wolfram|Alpha</a>. Scheint zu stimmen.</p> <h3>Basiswechselmatrix bestimmen</h3> <p>Für jedes Jordankästchen der Länge <code>$i$</code> muss nun 1 Vektor gewählt werden und <code>$i-1$</code> Vektoren müssen bestimmt werden. Dafür muss <code>$\Omega(\lambda) := A - \lambda \cdot E$</code> bestimmt werden.</p> <p><strong>Eigenwert -1</strong>: <code>$\Omega(-1) = \begin{pmatrix} 2 &amp; 2 &amp; 47 &amp; 11\\ 3 &amp; 3 &amp; 8 &amp; 15\\ 0 &amp; 0 &amp; 4 &amp; 1\\ 0 &amp; 0 &amp; 8 &amp; 2 \end{pmatrix}$</code></p> <p><code>$\begin{aligned} K_1(-1) &amp;= \text{Kern } \Omega(-1) \\ &amp;= \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 23.5 &amp; 5.5\\ 0 &amp; 0 &amp; -62.5 &amp; -5.5\\ 0 &amp; 0 &amp; 4 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 0\end{pmatrix} \\ &amp;= \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 1\end{pmatrix} \\ &amp;= \left [ \begin{pmatrix}1 \\ -1 \\ 0 \\ 0 \end{pmatrix} \right ] \end{aligned}$</code>.</p> <p><code>$\Omega(-1)^2 = \begin{pmatrix} 10 &amp; 10 &amp; 386 &amp; 121\\ 15 &amp; 15 &amp; 317 &amp; 116\\ 0 &amp; 0 &amp; 24 &amp; 6\\ 0 &amp; 0 &amp; 48 &amp; 12 \end{pmatrix}$</code>.</p> <p>Da das Kästchen die Größe 2 hat, benötigen wir noch <code>$K_2$</code>:</p> <p><code>$K_2(-1) = \left [ \begin{pmatrix} 1 \\ -1 \\ 0 \\ 0 \end{pmatrix}, \begin{pmatrix} \frac{49}{20} \\ 0 \\ \frac{1}{4} \\ -1 \end{pmatrix} \right ] = \left [ \begin{pmatrix} 1 \\ -1 \\ 0 \\ 0 \end{pmatrix}, \begin{pmatrix} 49 \\ 0 \\ 5 \\ -20 \end{pmatrix} \right ] $</code>.</p> <p>(Check mit <a href="http://www.wolframalpha.com/input/?i=NullSpace+%7B%7B2%2C2%2C47%2C11%7D%2C%7B3%2C3%2C8%2C15%7D%2C%7B0%2C0%2C4%2C1%7D%2C%7B0%2C0%2C8%2C2%7D%7D%5E2">Wolfram|Alpha</a>. Scheint zu stimmen.)</p> <p>Nun muss ein Vektor aus <code>$K_2(-1)$</code> gewählt werden, der nicht in <code>$K_1(-1)$</code> ist. Das ist dann der erste Basisvektor für unsere Basiswechselmatrix. Die Wahl ist hier eindeutig:</p> <p><code>$b_1 := \begin{pmatrix}49\\0\\5\\-20\end{pmatrix}$</code> <code>$b_2 := \Omega(-1) \cdot b_1 = \begin{pmatrix}113\\-113\\0\\0\end{pmatrix}$</code></p> <p><strong>Eigenwert 4</strong>: <code>$\Omega(4) = \begin{pmatrix} -3 &amp; 2 &amp; 47 &amp; 11\\ 3 &amp; -2 &amp; 8 &amp; 15\\ 0 &amp; 0 &amp; -1 &amp; 1\\ 0 &amp; 0 &amp; 8 &amp; -3 \end{pmatrix}$</code></p> <p><code>$K_1(4) = \left [ \begin{pmatrix} -\frac{2}{3} \\ - 1 \\ 0 \\ 0\end{pmatrix} \right ] = \left [ \begin{pmatrix} 2 \\ 3 \\ 0 \\ 0\end{pmatrix} \right ] \Rightarrow b_3 := \begin{pmatrix} 2 \\ 3 \\ 0 \\ 0\end{pmatrix}$</code></p> <p><strong>Eigenwert 5</strong>: <code>$\Omega(5) = \begin{pmatrix} -4 &amp; 2 &amp; 47 &amp; 11\\ 3 &amp; -3 &amp; 8 &amp; 15\\ 0 &amp; 0 &amp; -2 &amp; 1\\ 0 &amp; 0 &amp; 8 &amp; -4 \end{pmatrix}$</code></p> <p><code>$K_1(5) = \left [ \begin{pmatrix} -\frac{283}{12} \\ - \frac{359}{12} \\ -\frac{1}{2} \\ -1\end{pmatrix} \right ] = \left [ \begin{pmatrix} 283 \\ 359 \\ 6 \\ 12\end{pmatrix} \right ] \Rightarrow b_4 := \begin{pmatrix} 283 \\ 359 \\ 6 \\ 12\end{pmatrix}$</code></p> <p>Nun muss man die Vektoren noch in der richtigen Reihenfolge zusammensetzen. Da wir zuerst das -1 Jordankästchen, dann das 4er Jordankästchen und dann das 5er-Kästchen wollen, schreiben wir sie in dieser Reihenfolge auf: <code>$S = \begin{pmatrix}b_2 &amp; b_1 &amp; b_3 &amp; b_4\end{pmatrix} = \begin{pmatrix} 113 &amp; 49 &amp; 2 &amp; 283\\ -113 &amp; 0 &amp; 3 &amp; 359\\ 0 &amp; 5 &amp; 0 &amp; 6\\ 0 &amp; -20&amp; 0 &amp; 12\end{pmatrix}$</code></p> <p>Dann gilt:</p> <p><code>$S^{-1} = \frac{1}{101700} \cdot \begin{pmatrix} 540 &amp; -360 &amp; -4384 &amp; 227\\ 0 &amp; 0 &amp; 6780 &amp; -3390\\ 20340 &amp; 20340 &amp; -1517364 &amp; -329508\\ 0 &amp; 0 &amp; 1130 &amp; 2825\end{pmatrix}$</code> (<a href="http://www.wolframalpha.com/input/?i=inverse+%7B%7B113%2C49%2C2%2C283%7D%2C%7B-113%2C0%2C3%2C359%7D%2C%7B0%2C5%2C0%2C6%7D%2C%7B0%2C-20%2C0%2C12%7D%7D">Wolfram|Alpha</a>)</p> <p>Nun sollte <code>$J = S^{-1} \cdot A \cdot S$</code> gelten. Also, Schritt für Schritt:</p> <p><code>$S^{-1} \cdot A \cdot S = \frac{1}{101700} \cdot \begin{pmatrix} -540 &amp; 360 &amp; 1164 &amp; -3617\\ 0 &amp; 0 &amp; -6780 &amp; 3390\\ 81360 &amp; 81360 &amp; -6069456 &amp; -1318032\\ 0 &amp; 0 &amp; 56500 &amp; 14125 \end{pmatrix} \cdot S = \begin{pmatrix} -1 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 4 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 5 \end{pmatrix}$</code> (<a href="http://www.wolframalpha.com/input/?i=%7B%7B3%2F565%2C+-2%2F565%2C+-1096%2F25425%2C+227%2F101700%7D%2C+%7B0%2C+0%2C+1%2F15%2C+-1%2F30%7D%2C+%7B1%2F5%2C+1%2F5%2C+-373%2F25%2C+-81%2F25%7D%2C+%7B0%2C+0%2C+1%2F9%2C+1%2F36%7D%7D*%7B%7B1%2C2%2C47%2C11%7D%2C%7B3%2C2%2C8%2C15%7D%2C%7B0%2C0%2C3%2C1%7D%2C%7B0%2C0%2C8%2C1%7D%7D">Wolfram|Alpha</a> und <a href="http://www.wolframalpha.com/input/?i=%7B%7B-3%2F565%2C+2%2F565%2C+2791%2F25425%2C+-3617%2F101700%7D%2C+%7B0%2C+0%2C+-1%2F15%2C+1%2F30%7D%2C+%7B4%2F5%2C+4%2F5%2C+-1492%2F25%2C+-324%2F25%7D%2C+%7B0%2C+0%2C+5%2F9%2C+5%2F36%7D%7D*%7B%7B113%2C49%2C2%2C283%7D%2C%7B-113%2C0%2C3%2C359%7D%2C%7B0%2C5%2C0%2C6%7D%2C%7B0%2C-20%2C0%2C12%7D%7D">Schritt 2</a>)</p> <h3>Programmierung</h3> <p>Bei diesem Beispiel haben sowohl Python (numpy) als auch Wolfram|Alpha und Mathematica versagt:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">linalg</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">47</span><span class="p">,</span><span class="mi">11</span><span class="p">],[</span><span class="mi">3</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">8</span><span class="p">,</span><span class="mi">15</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">3</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">8</span><span class="p">,</span><span class="mi">1</span><span class="p">]]</span> <span class="n">S</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">113</span><span class="p">,</span><span class="mi">49</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">283</span><span class="p">],[</span><span class="o">-</span><span class="mi">113</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">3</span><span class="p">,</span><span class="mi">359</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">5</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">6</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">20</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">12</span><span class="p">]]</span> <span class="n">A</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="n">numpy</span><span class="o">.</span><span class="n">set_printoptions</span><span class="p">(</span><span class="n">precision</span><span class="o">=</span><span class="mi">2</span><span class="p">,</span> <span class="n">suppress</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="n">linewidth</span><span class="o">=</span><span class="mi">120</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;S^{-1} * A * S&quot;</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">A</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span></code></pre></div> <table> <tbody> <tr> <td>Wolfram</td> <td>Alpha hatte eine zu kleine Eingabegröße, Mathematica hat einfach gar nicht mehr reagiert und Python hat ein falsches Ergebnis ausgespuckt.</td> </tr> </tbody> </table> <h2>Beispiel 2</h2> <p>Gegeben sei die Matrix <code>$B \in \mathbb{C}^{4 \times 4}$</code>: <code>$B := \begin{pmatrix} -1 &amp; -2 &amp; 2 &amp; 2\\ 2 &amp; 0 &amp; 1 &amp; -1\\ 2 &amp; 1 &amp; 0 &amp; -1\\ 0 &amp; -2 &amp; 2 &amp; 1 \end{pmatrix}$</code></p> <h3>Jordannormalform bestimmen</h3> <p><strong>1. Charakteristisches Polynom berechnen:</strong> <code>$p_B(\lambda) = (1-\lambda)^2 \cdot (1+\lambda)^2$</code>.</p> <p>Daraus folgt:</p> <ul> <li>`$\lambda = 1$` ist Eigenwert mit der algebraischen Vielfachheit 2.</li> <li>`$\lambda = -1$` ist Eigenwert mit der algebraischen Vielfachheit 2.</li> </ul> <p>Es gibt also genau zwei Jordan-Blöcke in der Jordannormalform. Beide haben die Kantenlänge 2.</p> <p><strong>2. Anzahl der Jordankästchen bestimmen:</strong> <code>$\begin{align} \dim \text{Eig}(1) &amp;= \dim \text{Kern}(A-E)\\ &amp;= \dim \text{Kern }\begin{pmatrix} -2 &amp; -2 &amp; 2 &amp; 2\\ 2 &amp; -1 &amp; 1 &amp; 1\\ 2 &amp; 1 &amp; -1 &amp; -1\\ 0 &amp; -2 &amp; 2 &amp; 0 \end{pmatrix}\\ &amp;= \dim \text{Kern }\begin{pmatrix} 1 &amp; 1 &amp; -1 &amp; -1\\ 0 &amp; -3 &amp; 3 &amp; 3\\ 0 &amp; -1 &amp; 1 &amp; 1\\ 0 &amp; 1 &amp; -1 &amp; 0 \end{pmatrix}\\ &amp;= \dim \text{Kern }\begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; -1\\ 0 &amp; 1 &amp; -1 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 1 \end{pmatrix} \\ &amp;= \dim \left [\begin{pmatrix}0\\1\\1\\0\end{pmatrix} \right ] = 1 \end{align}$</code></p> <p>Analog: <code>$\begin{align} \dim \text{Eig}(-1) &amp;= \dim \text{Kern}(A-E)\\ &amp;= \dim \text{Kern }\begin{pmatrix} 0 &amp; -2 &amp; 2 &amp; 2\\ 2 &amp; 1 &amp; 1 &amp; 1\\ 2 &amp; 1 &amp; 1 &amp; -1\\ 0 &amp; -2 &amp; 2 &amp; 2 \end{pmatrix}\\ &amp;= \dim \text{Kern }\begin{pmatrix} 1 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 1 &amp; -1 &amp; -1\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix} \\ &amp;= \dim \left [\begin{pmatrix}1\\-1\\-1\\0\end{pmatrix}, \begin{pmatrix}0\\1\\0\\1\end{pmatrix} \right ] = 2 \end{align}$</code></p> <p>Also ist die Jordansche Normalform festgelegt:</p> <p><code>$J_B = \begin{pmatrix} -1 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 1 \end{pmatrix}$</code> → <a href="http://www.wolframalpha.com/input/?i=%7B%7B-1%2C-2%2C2%2C2%7D%2C%7B2%2C0%2C1%2C-1%7D%2C%7B2%2C1%2C0%2C-1%7D%2C%7B0%2C-2%2C2%2C1%7D%7D">Kontrolle mit Wolfram|Alpha</a></p> <h3>Basiswechselmatrix bestimmen</h3> <p>Für jedes Jordankästchen der Länge <code>$i$</code> muss nun 1 Vektor gewählt werden und <code>$i-1$</code> Vektoren müssen bestimmt werden. Dafür muss <code>$\Omega(\lambda) := A - \lambda \cdot E$</code> bestimmt werden.</p> <p><strong>Eigenwert 1:</strong> <code>$K_1(1) = \left [\begin{pmatrix}0\\1\\1\\0\end{pmatrix} \right ]$</code>. <code>$\begin{align} K_2(1) &amp;= \text{Kern}(\Omega(1)^2) \\ &amp;= \text{Kern }\begin{pmatrix} -2 &amp; -2 &amp; 2 &amp; 2\\ 2 &amp; -1 &amp; 1 &amp; 1\\ 2 &amp; 1 &amp; -1 &amp; -1\\ 0 &amp; -2 &amp; 2 &amp; 0 \end{pmatrix}^2 \\ &amp;= \text{Kern }\begin{pmatrix} 4 &amp; 4 &amp; -4 &amp; -4\\ -4 &amp; 0 &amp; 0 &amp; 4\\ -4 &amp; -4 &amp; 4 &amp; 4\\ 0 &amp; 4 &amp; -4 &amp; 0 \end{pmatrix}\\ &amp;= \text{Kern }\begin{pmatrix}\\ 1 &amp; 0 &amp; 0 &amp; -1\\ 0 &amp; 1 &amp; -1 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix} \\ &amp;= \left [ \begin{pmatrix}0\\1\\1\\0\end{pmatrix}, \begin{pmatrix}1\\0\\0\\1\end{pmatrix} \right ] \end{align}$</code></p> <p>Nun muss ein Vektor aus <code>$K_2(1)$</code> gewählt werden, der nicht in <code>$K_1(1)$</code> ist. Das ist dann der erste Basisvektor für unsere Basiswechselmatrix. Die Wahl ist hier eindeutig:</p> <p><code>$b_1 = \begin{pmatrix}1\\0\\0\\1\end{pmatrix}$</code>. <code>$b_2 = \Omega(1) \cdot b_1 = \begin{pmatrix}0\\1\\1\\0\end{pmatrix}$</code>. <code>$b_3 = \begin{pmatrix}1\\-1\\-1\\0\end{pmatrix}, ~~~ b_4 = \begin{pmatrix}0\\1\\0\\1\end{pmatrix}$</code>.</p> <p>Nun muss man die Vektoren noch in der richtigen Reihenfolge zusammensetzen. Da wir zuerst den -1 Jordanblock und dann den 1er-Jordanblock wollen, schreiben wir sie in dieser Reihenfolge auf: <code>$S = \begin{pmatrix}b_3 &amp; b_4 &amp; b_2 &amp; b_1\end{pmatrix} = \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 1\\ -1 &amp; 1 &amp; 1 &amp; 0\\ -1 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 1\end{pmatrix}$</code></p> <h3>Programmierung</h3> <p>Hier kann man mal schön ein paar Variationen ausprobieren:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">linalg</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[[</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">2</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">2</span><span class="p">],[</span><span class="mi">2</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">],[</span><span class="mi">2</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">2</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">1</span><span class="p">]]</span> <span class="c"># b3, b4, b2, b1</span> <span class="n">S</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">]]</span> <span class="c"># b2, b1, b3, b4 - zuerst 1er Block</span> <span class="n">S</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">]]</span> <span class="c"># Die Reihenfolge der Vektoren f&amp;uuml;r die Jordank&amp;auml;stchen innerhalb</span> <span class="c"># eines Jordanblocks ist egal</span> <span class="c"># b2, b1, b4, b3 = b2, b1, b3, b4 != alle anderen Reihenfolgen</span> <span class="n">S</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">]]</span> <span class="c"># Mit (b1, b2, b3, b4) ist die 1 auf der Nebendiagonale unten</span> <span class="n">S</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">]]</span> <span class="n">B</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="n">numpy</span><span class="o">.</span><span class="n">set_printoptions</span><span class="p">(</span><span class="n">precision</span><span class="o">=</span><span class="mi">2</span><span class="p">,</span> <span class="n">suppress</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="n">linewidth</span><span class="o">=</span><span class="mi">120</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;S^{-1} * B * S&quot;</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">B</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span></code></pre></div> <h2>Beispiel 3</h2> <p>Die Matrix aus diesem Beispiel ist aus der Klausur vom Frühjahr 2012 bei Prof. Dr. Wildericht Tuschmann.</p> <p>Gegeben sei die Matrix <code>$C \in \mathbb{R}^{4 \times 4}$</code>: <code>$C := \begin{pmatrix} 1 &amp; 0 &amp; -1 &amp; -1\\ -1 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 2 &amp; 1\\ 1 &amp; 1 &amp; 0 &amp; 1 \end{pmatrix}$</code>.</p> <h3>Jordannormalform bestimmen</h3> <p><strong>1. Charakteristisches Polynom berechnen:</strong> <code>$p_C(\lambda) = (\lambda - 1)^4$</code>.</p> <p>Es gibt also genau einen Jordan-Block in der Jordannormalform.</p> <p><strong>2. Anzahl der Jordankästchen bestimmen:</strong></p> <p><code>$ \begin{align} \Omega &amp;= \begin{pmatrix} 0 &amp; 0 &amp; -1 &amp; -1\\ -1 &amp; -1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 1\\ 1 &amp; 1 &amp; 0 &amp; 0 \end{pmatrix}\\ \Omega^2 &amp;= \begin{pmatrix} -1 &amp; -1 &amp; -1 &amp; -1\\ 1 &amp; 1 &amp; 1 &amp; 1\\ 1 &amp; 1 &amp; 1 &amp; 1\\ -1 &amp; -1 &amp; -1 &amp; -1 \end{pmatrix}\\ \Omega^3 &amp;= \begin{pmatrix} 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix} \end{align} $</code>.</p> <p><code>$\begin{align} \text{Eig}(1) &amp;= K_1(1) = \text{Kern}(\Omega) \\ &amp;= \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix}\\ &amp;= \left [ \begin{pmatrix}1\\-1\\0\\0\end{pmatrix}, \begin{pmatrix}0\\0\\1\\-1\end{pmatrix} \right ] \end{align} $</code></p> <p>Jetzt wissen wir, dass es zwei Jordankästchen gibt. Es gibt also zwei Möglichkeiten:</p> <ul> <li>Ein Jordank&auml;stchen hat die Gr&ouml;&szlig;e 1, dann muss das Andere die Gr&ouml;&szlig;e 3 haben.</li> <li>Ein Jordank&auml;stchen hat die Gr&ouml;&szlig;e 2, dann muss das Andere die Gr&ouml;&szlig;e 2 haben.</li> </ul> <p><code>$\begin{align} K_2(1) &amp;= \text{Kern}(\Omega^2) \\ &amp;= \text{Kern} \begin{pmatrix} 1 &amp; 1 &amp; 1 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix}\\ &amp;= \left [ \begin{pmatrix}1\\-1\\0\\0\end{pmatrix}, \begin{pmatrix}1\\0\\-1\\0\end{pmatrix}, \begin{pmatrix}1\\0\\0\\-1\end{pmatrix} \right ]\\ K_3(1) &amp;= \text{Kern}(\Omega^3) = \mathbb{R}^4\\ \end{align} $</code></p> <p>Da erst <code>$K_3(1) = \mathbb{R}^4$</code> ist das größte Jordankästchen von der Größe 3. Damit ergibt sich folgende Jordannormalform:</p> <p><code>$J = \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 1 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 1 \end{pmatrix}$</code></p> <h3>Basiswechselmatrix bestimmen</h3> <p>Für jedes Jordankästchen der Länge <code>$i$</code> muss nun 1 Vektor gewählt werden und <code>$i-1$</code> Vektoren müssen bestimmt werden. Dafür muss <code>$\Omega(\lambda) := C - \lambda \cdot E$</code> bestimmt werden.</p> <p><strong>Eigenwert 1:</strong> <strong>Kästchengröße 3</strong> <code>$b_1 \in K_3(1) \land b_1 \notin K_2(1) \Rightarrow b_1 \in \left [ \begin{pmatrix}1\\0\\0\\0\end{pmatrix} \right ]$</code>. Wähle <code>$b_1 = \begin{pmatrix}1\\0\\0\\0\end{pmatrix}$</code>.</p> <p><code>$b_2 = \Omega(b_1) = \begin{pmatrix}0\\-1\\0\\1\end{pmatrix}$</code>.</p> <p><code>$b_3 = \Omega^2(b_1) = \Omega(b_2)= \begin{pmatrix}-1\\1\\1\\-1\end{pmatrix}$</code></p> <p><strong>Kästchengröße 1</strong> <code>$b_4 = \begin{pmatrix}1\\-1\\0\\0\end{pmatrix}$</code></p> <p>Das 1-er Kästchen soll zuerst kommen, also muss <code>$b_4$</code> zuerst in die Basiswechselmatrix. Unsere gesuchte Matrix <code>$S$</code> für die oben angegebene JNF ist also: <code>$S = \begin{pmatrix} b_4 &amp; b_3 &amp; b_2 &amp; b_1 \end{pmatrix} = \begin{pmatrix} 1 &amp; -1 &amp; 0 &amp; 1\\ -1 &amp; 1 &amp; -1 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; 1 &amp; 0 \end{pmatrix} $</code></p> <p>Nun sollte <code>$J = S^{-1} \cdot C \cdot S$</code> gelten. Also, Schritt für Schritt:</p> <p><code>$\begin{align} S^{-1} \cdot C \cdot S &amp;= \begin{pmatrix} 0 &amp; -1 &amp; 0 &amp; -1\\ 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 1\\ 1 &amp; 1 &amp; 1 &amp; 1 \end{pmatrix} \cdot \begin{pmatrix} 1 &amp; 0 &amp; -1 &amp; -1\\ -1 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 2 &amp; 1\\ 1 &amp; 1 &amp; 0 &amp; 1 \end{pmatrix} \cdot \begin{pmatrix} 1 &amp; -1 &amp; 0 &amp; 1\\ -1 &amp; 1 &amp; -1 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; 1 &amp; 0 \end{pmatrix}\\ &amp;= \begin{pmatrix} 0 &amp; -1 &amp; 0 &amp; -1\\ 0 &amp; 0 &amp; 2 &amp; 1\\ 1 &amp; 1 &amp; 2 &amp; 2\\ 1 &amp; 1 &amp; 1 &amp; 1 \end{pmatrix} \cdot \begin{pmatrix} 1 &amp; -1 &amp; 0 &amp; 1\\ -1 &amp; 1 &amp; -1 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; 1 &amp; 0 \end{pmatrix} \\ &amp;= \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 1 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 1 \end{pmatrix} \end{align}$</code></p> <h3>Programmierung</h3> <p>Hier habe ich mal für Leute, die kein Python haben, als Kommentar das Ergebnis präsentiert. Ich denke damit ist klar, welchen Einfluss die Reihenfolge der Basisvektoren hat.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">linalg</span> <span class="n">numpy</span><span class="o">.</span><span class="n">set_printoptions</span><span class="p">(</span><span class="n">precision</span><span class="o">=</span><span class="mi">2</span><span class="p">,</span> <span class="n">suppress</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="n">linewidth</span><span class="o">=</span><span class="mi">120</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">],[</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">],[</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">]]</span> <span class="n">C</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">b1</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">]</span> <span class="n">b2</span> <span class="o">=</span> <span class="p">[</span><span class="mi">0</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">]</span> <span class="n">b3</span> <span class="o">=</span> <span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="n">b4</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">,</span><span class="mi">0</span><span class="p">]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b4</span><span class="p">,</span><span class="n">b1</span><span class="p">,</span><span class="n">b2</span><span class="p">,</span><span class="n">b3</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c"># [[ 1 0 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;4123&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 1 1 0]</span> <span class="c"># [ 0 0 1 1]]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b4</span><span class="p">,</span><span class="n">b1</span><span class="p">,</span><span class="n">b3</span><span class="p">,</span><span class="n">b2</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c">#[[ 1 0 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;4132&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 0 1 1]</span> <span class="c"># [ 0 1 0 1]]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b4</span><span class="p">,</span><span class="n">b2</span><span class="p">,</span><span class="n">b1</span><span class="p">,</span><span class="n">b3</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c"># [[ 1 0 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;4213&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 1 0]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 0 1 0]</span> <span class="c"># [ 0 1 0 1]]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b4</span><span class="p">,</span><span class="n">b2</span><span class="p">,</span><span class="n">b3</span><span class="p">,</span><span class="n">b1</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c"># [[ 1 0 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;4231&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 0 1]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 1 1 0]</span> <span class="c"># [ 0 0 0 1]]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b4</span><span class="p">,</span><span class="n">b3</span><span class="p">,</span><span class="n">b1</span><span class="p">,</span><span class="n">b2</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c"># [[ 1 0 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;4312&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 0 1]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 0 1 0]</span> <span class="c"># [ 0 0 1 1]]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b4</span><span class="p">,</span><span class="n">b3</span><span class="p">,</span><span class="n">b2</span><span class="p">,</span><span class="n">b1</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c"># [[ 1 0 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;4321&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 1 0]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 0 1 1]</span> <span class="c"># [ 0 0 0 1]]</span> <span class="n">S</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">([</span><span class="n">b3</span><span class="p">,</span><span class="n">b2</span><span class="p">,</span><span class="n">b1</span><span class="p">,</span><span class="n">b4</span><span class="p">])</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span> <span class="c"># [[ 1 1 0 0]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;3214&quot;</span><span class="p">)</span> <span class="c"># [ 0 1 1 0]</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">inv</span><span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="o">*</span> <span class="n">C</span> <span class="o">*</span> <span class="n">S</span><span class="p">)</span> <span class="c"># [ 0 0 1 0]</span> <span class="c"># [ 0 0 0 1]]</span></code></pre></div> Berechnung der euklidischen Normalform //martin-thoma.com/berechnung-der-euklidischen-normalform/ Mon, 10 Sep 2012 07:57:50 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/berechnung-der-euklidischen-normalform <p>Die euklidische Normalform einer linearen Isometrie, manchmal auch lineare Normalform gennant, hat folgende Gestalt:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/09/math-euklidische-normalform.png"><img src="../images/2012/09/math-euklidische-normalform.png" alt="Euklidische Normalform" width="" height="" class="size-full wp-image-43911 " /></a><p class="wp-caption-text">Euklidische Normalform</p></div> <p>Bei einer <span>(n \times n)</span>-Matrix gilt also folgende Gleichung: <span>(n = p + q + 2r)</span></p> <h2>Bestimmung der Normalform</h2> <p>Sei <span>(\Phi)</span> eine lineare Isometrie eines euklidischen Vektorraumes. Dann habe <span>(\Phi)</span> die Abbildungsmatrix <span>(A)</span>. Sei <span>(B := A + A^T)</span>. Wenn man die euklidische Normalform bilden will, bestimmt man zuerst das charakteristische Polynom von <span>(B)</span>. Die Nullstellen davon sind die Eigenwerte. Die algebraische Vielfachheit des Eigenwertes 2 von <span>(B)</span> (die Potenz im charakteristischen Polynom) gibt die Anzahl der 1er an, genauso gibt die Vielfachheit des Eigenwertes -2 die Anzahl der -1er an.</p> <p>Die restlichen Eigenwerte <span>(\lambda_1, \dots, \lambda_r)</span> geben die Drehkästchen an.</p> <p>Es gilt: <span>(\cos \omega = \frac{\lambda}{2})</span> <span>(\sin \omega = \sqrt{1 - \frac{\lambda^2}{4}})</span></p> <p>Mit diesen Angaben kann man direkt die euklidische Normalform angeben.</p> <h2 id="bestimmung-der-transformationsmatrix">Bestimmung der Transformationsmatrix</h2> <h3>Eigenräume bestimmen</h3> <p>Die Eigenräume berechnet man wie gewohnt:</p> <p><span>(\text{Eig}(\lambda_i) = \text{Kern}(B- \lambda_i \cdot E))</span></p> <h3>ONB bestimmen</h3> <p>Nun wählt man für jeden Eigenraum eine Basis Orthonormalbasis aus Eigenvektoren. Das kann man mit dem Gram-Schmidtsches Orthogonalisierungsverfahren machen, also: Wähle ein beliebiges <span>(w_1 \in \text{Eig}(\lambda_i))</span>.</p> <div>\[w_j = v_j - \sum_{i=1}^{j-1} \frac{\langle v_j, w_i \rangle}{\langle w_i, w_i \rangle} \cdot w_i\]</div> <h2 id="quellen">Quellen</h2> <ul> <li>Skript von Prof. Dr. Leuzinger, S. 228 ff.</li> <li>Klausur &bdquo;Lineare Algebra und analytische Geometrie&ldquo; vom Frühjahr 2007, Aufgabe II.4</li> </ul> How to check if a point is inside a rectangle //martin-thoma.com/how-to-check-if-a-point-is-inside-a-rectangle/ Fri, 07 Sep 2012 21:28:38 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-check-if-a-point-is-inside-a-rectangle <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/09/rectangle.png"><img src="../images/2012/09/rectangle.png" alt="A rectangle" width="" height="" class="size-full wp-image-43611 " /></a><p class="wp-caption-text">A rectangle</p></div> <p>I’ve just found this interesting question on <a href="http://math.stackexchange.com/q/190111/6876">StackExchange</a>:</p> <p>If you have a rectangle ABCD and point P. Is P inside ABCD?</p> <h2 id="the-idea">The idea</h2> <p>The idea how to solve this problem is simply beautiful.</p> <p>If the point is in the rectangle, it divides it into four triangles:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/09/rectangle-2.png"><img src="../images/2012/09/rectangle-2.png" alt="Divided rectangle" width="" height="" class="size-full wp-image-43651 " /></a><p class="wp-caption-text">Divided rectangle</p></div> <p>If P is not inside of ABCD, you end up with somethink like this:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/09/rectangle-3.png"><img src="../images/2012/09/rectangle-3.png" alt="Point is outside of rectangle " width="" height="" class="size-full wp-image-43661 " /></a><p class="wp-caption-text">Point is outside of rectangle</p></div> <p>You might note that the area of the four triangles in is bigger than the area of the rectangle. So if the area is bigger, you know that the point is outside of the rectangle.</p> <h2 id="formulae">Formulae</h2> <p>If you know the coordinates of the points, you can calculate the area of the rectangle like this:</p> <p><code>$A_\text{rectangle} = \frac{1}{2} \left| (y_{A}-y_{C})\cdot(x_{D}-x_{B}) + (y_{B}-y_{D})\cdot(x_{A}-x_{C})\right|$</code></p> <p>The area of a triangle is: <code>$A_\text{triangle} = \frac{1}{2} (x_1(y_2-y_3) + x_2(y_3-y_1) + x_3(y_1-y_2))$</code></p> <h2 id="python">Python</h2> <div class="important">Please look at Jans comment. There is an error in my Python code, but I don't have the time to correct it.</div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">isPinRectangle</span>(r, P): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> r: A list of four points, each has a x- and a y- coordinate</span><span> </span><span> P: A point</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> areaRectangle = <span style="color:#60E">0.5</span>*<span style="color:#369;font-weight:bold">abs</span>( <span style="color:#777"># y_A y_C x_D x_B</span> (r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>])*(r[<span style="color:#00D">3</span>][<span style="color:#00D">0</span>]-r[<span style="color:#00D">1</span>][<span style="color:#00D">0</span>]) <span style="color:#777"># y_B y_D x_A x_C</span> + (r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>])*(r[<span style="color:#00D">0</span>][<span style="color:#00D">0</span>]-r[<span style="color:#00D">2</span>][<span style="color:#00D">0</span>]) ) ABP = <span style="color:#60E">0.5</span>*( r[<span style="color:#00D">0</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">1</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">2</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]) ) BCP = <span style="color:#60E">0.5</span>*( r[<span style="color:#00D">1</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">2</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">3</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>]) ) CDP = <span style="color:#60E">0.5</span>*( r[<span style="color:#00D">2</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">3</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">0</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">2</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>]) ) DAP = <span style="color:#60E">0.5</span>*( r[<span style="color:#00D">3</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">0</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">1</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>]) +r[<span style="color:#00D">1</span>][<span style="color:#00D">0</span>]*(r[<span style="color:#00D">3</span>][<span style="color:#00D">1</span>]-r[<span style="color:#00D">0</span>][<span style="color:#00D">1</span>]) ) <span style="color:#080;font-weight:bold">return</span> areaRectangle == (ABP+BCP+CDP+DAP) </pre></div> </div> </div> <h2 id="triangle">Triangle</h2> <p>The same idea can easily be adopted to triangles:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">Point</span>: <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Represents a two dimensional point.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">__init__</span>(<span style="color:#069">self</span>, x, y): <span style="color:#069">self</span>.x = x <span style="color:#069">self</span>.y = y <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">__get__</span>(<span style="color:#069">self</span>, obj, cls=<span style="color:#069">None</span>): <span style="color:#080;font-weight:bold">return</span> obj <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">__repr__</span>(<span style="color:#069">self</span>): <span style="color:#080;font-weight:bold">return</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">P(%.2lf|%.2lf)</span><span style="color:#710">&quot;</span></span> % (<span style="color:#069">self</span>.x, <span style="color:#069">self</span>.y) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">__str__</span>(<span style="color:#069">self</span>): <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">repr</span>(<span style="color:#069">self</span>) <span style="color:#080;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">Triangle</span>: <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Represents a triangle in R^2.</span><span style="color:black">&quot;&quot;&quot;</span></span> epsilon = <span style="color:#60E">0.001</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">__init__</span>(<span style="color:#069">self</span>, a, b, c): <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">isinstance</span>(a, Point) <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">isinstance</span>(b, Point) <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">isinstance</span>(c, Point) <span style="color:#069">self</span>.a = a <span style="color:#069">self</span>.b = b <span style="color:#069">self</span>.c = c <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">getArea</span>(<span style="color:#069">self</span>): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Get area of this triangle.</span><span> </span><span> &gt;&gt;&gt; Triangle(Point(0.,0.), Point(10.,0.), Point(10.,10.)).getArea()</span><span> </span><span> 50.0</span><span> </span><span> &gt;&gt;&gt; Triangle(Point(-10.,0.), Point(10.,0.), Point(10.,10.)).getArea()</span><span> </span><span> 100.0</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> a, b, c = <span style="color:#069">self</span>.a, <span style="color:#069">self</span>.b, <span style="color:#069">self</span>.c <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">abs</span>(a.x*(b.y-c.y)+b.x*(c.y-a.y)+c.x*(a.y-b.y))/<span style="color:#00D">2</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">isInside</span>(<span style="color:#069">self</span>, p): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Check if p is inside this triangle.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">assert</span> <span style="color:#369;font-weight:bold">isinstance</span>(p, Point) currentArea = <span style="color:#069">self</span>.getArea() pab = Triangle(p,<span style="color:#069">self</span>.a, <span style="color:#069">self</span>.b) pac = Triangle(p,<span style="color:#069">self</span>.a, <span style="color:#069">self</span>.c) pbc = Triangle(p,<span style="color:#069">self</span>.b, <span style="color:#069">self</span>.c) newArea = pab.getArea()+pac.getArea()+pbc.getArea() <span style="color:#080;font-weight:bold">return</span> (<span style="color:#369;font-weight:bold">abs</span>(currentArea - newArea) &lt; Triangle.epsilon) <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">doctest</span> doctest.testmod() </pre></div> </div> </div> <h2 id="credits">Credits</h2> <p>Thank you Teon Brooks for reporting an error (I wrote “rectangles” instead of “triangles”)</p> Bundeswettbewerb Informatik //martin-thoma.com/bundeswettbewerb-informatik/ Tue, 04 Sep 2012 11:42:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/bundeswettbewerb-informatik <div style="width: 138px" class="wp-caption alignright"><a href="../images/2012/09/bwinf-thumb.png"><img src="../images/2012/09/bwinf-thumb.png" alt="Logo des BwInf" width="" height="" class="size-full wp-image-43131" /></a><p class="wp-caption-text">Logo des BwInf</p></div> <p>Die erste Runde des 31. Bundeswettbewerb Informatik (kurz: BwInf) begann heute. Das bedeutet, bis zum 03.12.2012 haben Schüler mal wieder die Chance zu zeigen, was sie in der Informatik drauf haben. Es gibt keine verpflichtende Anmeldung, nur die Einsendung. Wenn ihr diesen Beitrag also vor dem 03.12.2012 lest, könnt ihr noch teilnehmen.</p> <p>Die offiziellen Informationen zum Wettbewerb, dessen <a href="http://www.bundeswettbewerb-informatik.de/index.php?id=629">Ablauf</a>, die <a href="http://www.bundeswettbewerb-informatik.de/index.php?id=628">Teilnahmebedingungen</a> und die <a href="http://www.bundeswettbewerb-informatik.de/index.php?id=1161">Aufgaben</a> gibt es auf <a href="http://www.bundeswettbewerb-informatik.de/">bundeswettbewerb-informatik.de</a>. Das Folgende ist inoffiziell; es sind meine persönlichen Erfahrungen.</p> <p>Ich habe selbst ein paar mal am Bundeswettbewerb teilgenommen und bin bei meiner letzten Teilnahme Bundessieger geworden. Später habe ich Musterlösungen erstellt und an der Korrektur der Erstrunden- und Zweitrundenaufgaben teilgenommen. Ich weiß also wovon ich rede.</p> <h2>Aufbau des Wettbewerbs</h2> <p>Der BwInf besteht aus drei Runden, in denen algorithmische Probleme gelöst werden müssen. Die ersten beiden Runden werden von zu Hause erledigt. Dafür habt ihr mehr als genug Zeit - jeweils über einen Monat. Die dritte Runde müsst ihr vor Ort bestehen. Diese läuft vollkommen anders ab, aber darüber will ich mal noch nichts berichten. (Falls ihr unbedingt einen Bericht wollt, hier ist der von <a href="http://www.tobias-thierer.de/endrunde.html">Tobias</a>).</p> <p>Nur wer in der ersten Runde mindestens drei von fünf (+ 3 Junioraufgaben) Aufgaben weitgehend richtig gelöst hat, wird zur Zweiten zugelassen. Die Aufgaben der zweiten Runde sind prinzipiell ähnlich aufgebaut, jedoch deutlich schwerer zu lösen. Immer wieder sind <code>$\mathcal{NP}$</code>-vollständige Probleme dabei.</p> <h2>Warum sollte man teilnehmen?</h2> <p>Programmiert ihr gerne? Habt ihr Spaß daran, an Aufgaben zu knobeln? Denkt ihr darüber nach, wie man bereits gelöste Probleme noch effizienter lösen kann?</p> <p>Dann ist der Bundeswettbewerb auf jeden Fall etwas für euch!</p> <p>Selbst wenn ihr nicht alle Fragen überzeugt mit einem „Ja“ beantworten könnt, könnte der Bundeswettbewerb euch gefallen. Probier es einfach mal aus.</p> <p>Einen weiteren Anreitz bieten Preise: Die Bundessieger werden soweit ich weiß immer in die Studienstiftung aufgenommen und es gibt Geldpreise.</p> <p>Und noch ein Schlusswort zur Motivation: Eine gute Dokumentation zu schreiben ist anstrengend. Ich hatte häufig bei der Dokumentation keine Lust mehr, sie noch ein weiteres mal anzusehen. Sie nochmals zu verbessern. Aber die Arbeit lohnt sich. Wenn ihr sie fertig geschrieben habt, könnt ihr stolz darauf sein. Wie ein Sprichwort so schön sagt: „Ohne Fleiß kein Preis.“</p> <h2>Tipps zur Aufgabenbearbeitung</h2> <h3>Zur L&ouml;sungsfindung</h3> <p>Wenn ihr ein Skript habt, dass eventuell nicht sofort, aber nach ein paar Stunden die Lösung ausgeben sollte, dann vergesst nicht, auch eine Ausgabe mit Zwischenergebnissen dafür einzubauen! Kaum etwas ist ärgerlicher, als ein Programm, das lange läuft und am Ende keine Ausgabe macht oder sich aufhängt.</p> <h3>Doku ist wichtig</h3> <p>Bei der Korrektur wird zuerst die Dokumentation angesehen. Natürlich ist die Lösungsidee wichtig, aber eine negativ bewertete Dokumentation ist ärgerlich. Also lest euch bitte die Dokumentation nochmals durch und überprüft, ob die wichtigen Lösungsideen verständlich erklärt wurden.</p> <p>Ich denke das ist wohl der einzige Aspekt, wo euch andere helfen können. Gerade Leute ohne Programmierkenntnis sollten eure Lösungsidee verstehen können. Mein Vater (der nicht programmieren kann) hat häufig meine Einseundungen nochmals auf Rechtschreib- und Grammatikfehler sowie auf fehlende Zusammenhänge überprüft. Er konnte zwar nicht sagen, was dort nicht stimmt, hat aber häufig … naja, sagen wir mal Stellen gefunden, bei denen meine Deutschlehrer wohl Zahnschmerzen hätten (trifft wohl auch auf diesen Blog zu ;-) )</p> <p>Also: Schreibt die Doku früh. Ich habe sie geschrieben, während ich programmiert habe. Dann setzt irgendwann eine Version auf, von der ihr denkt, dass sie fertig ist. Wartet so ein, zwei Tage und lest sie euch nochmals durch (es ist wirklich erstaunlich, was man dann sieht). Dann sucht euch jemanden, der die Aufgabenstellung nicht kennt und nicht programmieren kann. Der Korrekturleser sollte das Deutsche natürlich gut beherrschen. So ein Korrekturleser streicht nur mangelhafte Stellen in eurer endgültigen Version an, macht aber keine Verbesserungsvorschläge. Die müsst ihr euch selbst überlegen. Und dann ist man wirklich froh, wenn man das blöde Ding los ist.</p> <p>Eine Randbemerkung dazu noch: Ich habe mal einen kurzen Job als Programmierer für ein größeres Projekt übernommen. Dabei gab es über 2GB, die größtenteils C++-Code und ein paar Testdaten waren (rechnet es aus, das ist VERDAMMT viel Code!). Die hatten keine Dokumentation! Ich habe bestimmt eine Woche nur damit verbracht, mich mehr oder weniger wahllos durch wirre Quelltexte zu klicken, weil ich noch nicht einmal wusse, wo ich genau anfangen soll. Ich glaube den Zweck einer Dokumentation versteht man erst nach einem solchem Erlebnis.</p> <h3>Beispiele</h3> <p>Die Beispiele werden leider hin und wieder vergessen und sind oft nicht aussagekräftig. Überlegt euch: Welche Eingaben sind Standard-Fälle? Welche Eingaben sind Sonderfälle? Diese sollten unbedingt als Beispiele gezeigt werden, da es oft nicht klar ist, ob jemand in einer Einsendung daran gedacht hat. Mit Sonderfällen sind nicht falsche Eingaben gemeint - das ist für den Bundeswettbewerb unwichtig - sondern korrekt formatierte Eingaben, die etwas ungewöhnliches / schweres aufweisen.</p> <p>Die Beispiele sollen euch helfen, Probleme zu entdecken. Eventuell funktioniert eure Implementierung nicht so, wie ihr es euch vorstellt. Das könnt ihr damit feststellen. In diesem Zusammenhang solltet ihr euch das Konzept der <a href="http://de.wikipedia.org/wiki/Testgetriebene_Entwicklung">testgetriebenen Entwicklung</a> ansehen. Dabei schreibt man zuerst alle wichtigen Testfälle, bevor man überhaupt eine Zeile produktiven Codes schreibt. Beispielsweise für die Aufgabe „Verben“ würde ich heute so eine Herangehensweise wählen.</p> <p>Ach ja: Es kann sein, dass ihr ein Problem feststellt, dieses aber nicht beheben könnt. Dann solltet ihr es beschreiben. Es wird sowieso entdeckt. Man kann eurer Lösungsidee erkennen, welche schwächen die Implementierung hat.</p> <h3>Versionskontrolle</h3> <p>Ich habe leider erst nach dem Bundeswettbewerb meine ersten Erfahrungen mit Versionskontrollsystemen gesammelt. Immer wenn ich eine Idee hatte, wie man das Problem anders angehen könnte, habe ich eine Kopie der aktuellen Version erstellt und auf der Kopie weiter gearbeitet. Diese Lösung ist jedoch in vielerlei Hinsicht einem Versionskontrollsystem - <a href="http://wiki.ubuntuusers.de/Subversion">SVN</a> und <a href="http://wiki.ubuntuusers.de/Git">Git</a> sind die bekanntesten - unterlegen. Man kann nicht so leicht eine Sicherung durchführen. Es ist unübersichtlich, die wiederherstellung bei vielen Dateien ist schwer und man kann sich nicht so leicht die Unterschiede von verschiedenen Versionen anzeigen lassen. Zum vergleich: <a href="http://code.google.com/p/pychess/source/diff?spec=svn05804049a2723955ec26cdbaea3b40811273f37f&amp;r=05804049a2723955ec26cdbaea3b40811273f37f&amp;format=side&amp;path=/create_theme_preview.py">Hier</a> kann man sich den Unterschied zweier Versionen auf code.google.com ansehen. Mit <a href="http://wiki.ubuntuusers.de/Meld">meld</a> bekommt man ähnlich gute Ergebnisse auch auf dem eigenem Rechner.</p> <h3>LaTeX</h3> <p>LaTeX ist toll - aber keine Pflicht. Es werden leider relativ wenige Dokumentationen mit LaTeX erstellt. Dabei bietet LaTeX für den BwInf ein paar Vorteile:</p> <ul> <li>Das Ergebnis kann sich sehen lassen, LaTeX sieht einfach sch&ouml;n aus.</li> <li>Man kann die Doku in die Versionskontrolle stecken.</li> <li>Man kann Quelltext automatisch einbinden lassen (siehe dazu ein <a href="../how-to-print-source-code-with-latex/">Blogpost</a> von mir).</li> <li>Und so bekommt man LaTeX: <a href="../how-to-install-the-latest-latex-version/">How to install the latest LaTeX Version</a>.</li> </ul> <p>Außerdem ist die Kombination <a href="../latex-versioning-a-great-experience/">LaTeX+Versionskontrolle</a> toll ☺</p> <h3>Die CD</h3> <p>Ich weiß leider nicht, warum keine Online-Abgabe möglich ist. Vielleicht, weil es einfacher ist. Eventuell aus Sicherheitsgründen. Wenn man Papier und eine CD in der Hand hat, kann es nicht passieren, dass eine Runde im schlimmsten Szenario komplett ausfallen muss, weil der Server abgeraucht ist. Egal wie, ihr müsst die CD erstellen. Dazu hätte ich - aus Sicht eines Korrektors - ein paar Bitten:</p> <p>Die CD hat über 600 MB. Das ist deutlich mehr, als ihr braucht. Also schreibt doch bitte auch die Beispiele des BwInf darauf, sowie eine PDF-Datei eurer Doku. Das erleichtert die Korrektur ungemein, da man so die Doku durchsuchen kann. Überprüft, ob die CD auch wirklich gebrannt wurde, abgeschlossen wurde und sie lesbar ist. Wenn eure Dokumentation schlecht ist und die CD nicht lesbar ist, kann eventuell eine gute Lösungsidee schlecht bewertet werden.</p> <p>edit: Hier habe ich eine Rückmeldung von Herrn Dr. Pohl erhalten. Es geht nicht um CD vs. Online-Abgabe sondern um CD und „gedruckte Dokumentation und CD“ vs. „Online-Abgabe“. Die Korrektur von Lösungsideen auf einem Blatt Papier ist immer noch die einfachste und für den Leser die angenehmste. Ich schreibe als Korrektor häufig Anmerkungen in eure Dokumentation, damit der Zweitkorrektor leichter nachvollziehen kann, was ich mangelhaft oder auch sehr gut gefunden habe. Außerdem schreibe ich manchmal rein, was der Einsender gemeint hat (falls die Doku nicht so toll war und es nicht direkt ersichtlich ist). Außerdem ist es mit CDs einfacher, die Infrastruktur für die Korrektur aufzubauen. An den Bewertungswochenenden werden so ca. 30 frisch aufgesetzte, unvernetzte PCs benutzt (es lohnt sich also nicht, Viren zu schreiben). Bei einer Online-Abgabe müssten diese PCs Internet haben, was leider nicht immer zur Verfügung steht. Oder sie müssten lokal, z.B. auf einem NAS, sein. Das ist alles etwas umständlicher als einfach eine CD zu brennen. Ihr dürft übrigens auch SD-Karten einschicken ☺</p> <p>Vielen Dank an Herrn Dr. Pohl für die Hinweise!</p> <h2>Die Programmiersprache</h2> <p>Also eine <a href="http://de.wikipedia.org/wiki/Brainfuck">Brainfuck</a>-Einsendung muss jetzt nicht gerade sein (obwohl ich wirklich beeindruckt wäre). Aber eine <a href="http://de.wikipedia.org/wiki/Shakespeare_Programming_Language">Shakespeare</a>-Einsendung würde ich mal toll finden ☺ Nein, im ernst: Ihr dürft fast alles benutzen. Ich selbst kann Python, PHP, Java, C++ und C gut genug um jede Einsendung verstehen zu können. Ich weiß, dass wir immer Leute haben die Haskel/Objective CAML und vielleicht noch ein paar weitere funktionale Sprachen können. Auch Pascal, Delphi (Object Pascal), BASIC stellen kein Problem dar. Das ist jetzt keine vollständige Liste; unter den Korrektoren gibt es einige, die auch exotische Sprachen können. Aber wenn euch klar ist, dass eure Sprache exotisch ist, dann solltet ihr besondere Sprachfeatures kommentieren.</p> <p>Ich habe damals meine Einsendung in PHP geschrieben, später in Python. Warum PHP? Naja, es gibt ein super <a href="http://tut.php-quake.net/de/">Tutorial für PHP</a>.</p> <p>Welche Programmiersprache würde ich heute nehmen? Nun, es gibt keine Programmiersprache die für jeden Zweck gut ist. Für kleine Probleme - und Bundeswettbewerbsaufgaben sind zwar schwer, aber doch recht übersichtlich - eignet sich häufig Python gut. Falls es in der zweiten Runde auf Geschwindigkeit ankommt, ist wohl C++ eine Sprache der Wahl. Für später empfiehlt es sich, Java zu lernen. Aber ihr müsst keine dieser Sprachen nehmen. Das ist ja das tolle am BwInf. Es steht euch frei, das zu wählen, was für euch das beste ist.</p> <h2>Quelltext-Kommentare</h2> <p>Trotz Doku sind Quelltextkommentare erwünscht. Allerdings müssen Standard-Strukturen (if/else,for,while, Variablendeklarationen) nicht kommentiert werden! Übertreibt es nicht, aber verwendet Kommentare, wenn einem Außenstehendem nicht direkt klar sein kann, was ihr macht. Java-Programmierer sollten definitiv die standard Sun <a href="http://de.wikipedia.org/wiki/Checkstyle">Checkstyle</a> und <a href="http://de.wikipedia.org/wiki/Javadoc">JavaDoc</a> verwenden, Python-Programmierer sollten <a href="http://www.python.org/dev/peps/pep-0257/#one-line-docstrings">DocStrings</a> kennen und verwenden. Für alle anderen Sprachen muss man halt ein Gefühl entwickeln. Wer in C wild mit Pointern um sich wirft sollte tendenziell wohl mehr Kommentare machen als jemand, der Pythons Standardbefehle nutzt.</p> <h3>Style-Guides</h3> <p>Es ist nicht zwingend erforderlich, dass ihr euch an sogenannte Styel-Guides haltet. Allerdings ist es bei der Bewertung - und insbesondere später, wenn ihr an echten Projekten mit anderen zusammen arbeitet - sehr hilfreich, wenn ihr euch an Konventionen haltet. Hier sind ein paar:</p> <ul> <li><b>C++</b>: von <a href="https://google.github.io/styleguide/cppguide.html">Google</a></li> <li><b>Java</b>: <a href="https://google.github.io/styleguide/javaguide.html">Google</a> oder <a href="http://www.oracle.com/technetwork/java/codeconvtoc-136057.html">Oracle</a></li> <li><b>Python</b>: <a href="https://www.python.org/dev/peps/pep-0008/">PEP8</a>, <a href="http://pep8online.com/">Online-Checker</a>, <a href="https://github.com/numpy/numpy/blob/master/doc/HOWTO_DOCUMENT.rst.txt">NumpyDoc</a></li> </ul> <h2>Was sollte man lernen?</h2> <p>Falls ihr Informatik studieren wollt oder später programmieren wollt, sind SVN und GIT unverzichtbar. Außerdem werdet ihr wohl mit Java und C++ in Kontakt kommen. Am <a href="http://de.wikipedia.org/wiki/Karlsruher_Institut_f%C3%BCr_Technologie">KIT</a> wird euch beigebracht, wie ihr mit Eclipse und checkstyle umgeht. Aber es wird auch erwartet, dass ihr es nutzt. Ich vermute, dass für viele wissenschaftliche Veröffentlichungen im Natur- und Ingenieurswissenschaftlichen Bereich LaTeX kaum wegzudenken ist. (Ach ja: Ihr könnt auch <a href="../briefe-mit-latex-schreiben/" title="Briefe mit LaTeX schreiben">Briefe mit LaTeX schreiben</a> und <a href="../complex-latex-visualizations-tikz/" title="Complex LaTeX visualizations (Tikz)">komplexe Grafiken mit LaTeX erstellen</a>!)</p> <h3>Website-Empfehlungen</h3> <p>Das meiste, was ihr wissen müsst, könnt ihr über Wikipedia lernen. Ich habe mich z.B. mal durch die <a href="http://de.wikipedia.org/wiki/Kategorie:Algorithmus">Kategorie:Algorithmus</a> geklickt. Das ist nicht sonderlich zielführend und sicher nicht jedermanns Sache, aber so habe ich mir einiges beigebracht. Ob es mir viel genutzt hat, kann ich nur schwer beurteilen.</p> <p>Wenn ihr Interessantes rund um die praktische Informatik in kleinen Portionen lernen wollt, ist der Newsletter von <a href="http://stackoverflow.com/">StackOverflow.com</a> empfehlenswert. Der ist zwar auf englisch, aber ich glaube das Englisch ist einfach genug. Außerdem werdet ihr im Informatik-Bereich häufig auf englische Literatur, Websites, Manuals oder Spezifikationen treffen. Man muss sich vielleicht mal daran gewöhnen, mit <a href="http://dict.leo.org">leo</a> einiges Übersetzen, aber das gibt sich schnell.</p> <p>Es gibt übrigens von einigen Universitäten Online-Vorlesungen. Ich habe mir damals eine <a href="http://ocw.mit.edu/courses/#electrical-engineering-and-computer-science">Vorlesung vom MIT</a> komplett angesehen (das waren damals zwei Dozenten, von denen einer Prof. John Guttag war). Dieses Semester habe ich vom Stanford <a href="https://class.coursera.org/algo-2012-002/class/index">Algorithms: Design and Analysis</a> durchgearbeitet. Die stellen sogar eine PDF-Urkunde mit deinen Ergebnissen aus. <a href="http://www.udacity.com/">Udacity</a> bietet in der Hinsicht auch interessante Kurse.</p> <p>Wenn ihr generell am Knobeln Spaß habt, kann ich sogenannte „<a href="../challenge-websites/">Challenge Websites</a>“ empfehlen. Die Probleme sind (größtenteils) schneller zu lösen als beim Bundeswettbewerb und man muss keine Doku schreiben.</p> <h3>Buchempfehlungen</h3> <p>Für die zweite Runde kann ich „Computers and Intractability: A Guide to the Theory of NP-Completeness“ (<a href="http://de.wikipedia.org/wiki/Vorlage:BibISBN/0716710455">Link</a>) empfehlen. Es wird in der zweiten Runde häufig (immer?) erwartet, dass man auf die Komplexität des Problems bzw. das Laufzeitverhalten der eigenen Lösung eingeht. Wenn man das besonders gut macht, gibt es hin und wieder Bonuspunkte. Wenn ihr dieses Buch - das ganz eindeutig dem Bereich der Theoretischen Informatik zuzuordnen ist und für einen Schüler bestimmt keine leichte Lektüre ist - versteht und das Wissen übertragen könnt, dann könntet ihr hier Boni erhalten. Aber wie gesagt, das zu verstehen und auf ein konkretes Problem zu übertragen ist nicht leicht.</p> <p>Deutlich einfacher ist „Theoretische Informatik - kurz gefasst“. Das Buch gibt eine grundlegende Einleitung und ist auf deutsch.</p> <p>Und, nur um es nochmals zu betonen: Das sind persönliche Erfahrungen und teilweise Bitten von jemanden, der es korrigiert. Wenn Teilnehmer meine Tipps nicht beachten, gibt es keinen Punktabzug und es gibt auch keine Bonuspunkte, wenn ihr sie beachtet. Aber ihr erleichtert ein paar Leuten die Korrektur, ihr lernt dabei eventuell was neues (LaTeX und GIT/SVN werdet ihr im Informatik-Studium noch benötigen) und vielleicht fallen euch Fehler oder Mängel in eurer Lösung auf.</p> <p>Falls ihr Fragen habt kann ich die auch gerne beantworten. Auf <a href="http://ikhaya.ubuntuusers.de/2012/09/01/der-31-bundeswettbewerb-informatik-startet/">Ikhaya</a> habe ich bereits ein paar beantwortet.</p> <h2 id="siehe-auch">Siehe auch</h2> <ul> <li><a href="http://bwinf-tipps.de/">bwinf-tipps.de</a></li> <li><a href="http://tobias-thierer.de/bwinf_runde1-2.html">tobias-thierer.de</a></li> </ul> Nobel Prize in Physics 2009 //martin-thoma.com/nobel-prize-in-physics-2009/ Sat, 01 Sep 2012 11:09:36 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/nobel-prize-in-physics-2009 <p>Did you know how the election for a <a href="http://en.wikipedia.org/wiki/Nobel_Prize">Nobel Prize</a> works? Have you ever heard of a <a href="http://en.wikipedia.org/wiki/Charge-coupled_device">CCD</a>? I guess you know <a href="http://en.wikipedia.org/wiki/Optical_fiber">fiberoptics</a>?</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/8Nt1or4tHD4" frameborder="0" allowfullscreen=""></iframe> <p>I’ve found this clip via <a href="http://forschungspreisen.de/post/30594203694/nobelpreis-2009-ccd-und-glasfaseroptik-wie">forschungspreisen.de</a>, a german blog about science.</p> <h2>See also</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/List_of_Nobel_laureates">List of Nobel laureates</a></li> <li><a href="http://en.wikipedia.org/wiki/List_of_Nobel_laureates_by_country">List of Nobel laureates by country</a></li> <li><a href="http://en.wikipedia.org/wiki/List_of_Nobel_laureates_by_university_affiliation">List of Nobel laureates by university affiliation</a></li> </ul> How to reverse engineer a function //martin-thoma.com/how-to-reverse-engineer-a-function/ Mon, 27 Aug 2012 09:49:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-reverse-engineer-a-function <p>I am currently improving many articles on Wikipedia as a preparation for some math exams. And I recently started to create images with LaTeX / TikZ.</p> <p>Today, I’ve found <a href="http://commons.wikimedia.org/wiki/File:Intermediatevaluetheorem.png">this image</a> in the article about the Intermediate value theorem:</p> <div style="width: 337px" class="wp-caption aligncenter"><a href="../images/2012/08/Intermediatevaluetheorem.png"><img src="../images/2012/08/Intermediatevaluetheorem.png" alt="Pixel-image of a function from Wikipedia" width="" height="" class="size-full wp-image-42411" /></a><p class="wp-caption-text">Pixel-image of a function from Wikipedia</p></div> <h2>Get special points</h2> <p>As a first step, you should open the image with <a href="http://en.wikipedia.org/wiki/GIMP">GIMP</a> (or any other editor of your choice) and find the pixel-coordinates of special points:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/function-in-gimp.png"><img src="../images/2012/08/function-in-gimp.png" alt="Cubic function in GIMP" width="" height="" class="size-full wp-image-42441" /></a><p class="wp-caption-text">Cubic function in GIMP</p></div> <p><del datetime="2012-08-30T08:36:40+00:00">This function has a maximum at (123 | 105) and a minimum at (172 | 218)</del> … well, thats not correct. Note that the axis of GIMP starts at the upper left. So the y-axis is wrong.</p> <p>I have cropped and flipped the image vertically. Now you can read the minimum / maximum coordinates with GIMP:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/gimp-function-cropped-flipped.png"><img src="../images/2012/08/gimp-function-cropped-flipped.png" alt="Cubic function cropped and flipped vertically" width="" height="" class="size-full wp-image-42631" /></a><p class="wp-caption-text">Cubic function cropped and flipped vertically</p></div> <table> <tbody> <tr> <td>The local maximum is at (79</td> <td>133) and the local minimum is at (131</td> <td>20).</td> </tr> </tbody> </table> <h2>Form equations</h2> <p>A cubic function generally looks like this: <code>$f(x) = a \cdot x^3 + b \cdot x^2 + c \cdot x + d$</code></p> <p>You have two points, so they have to fit to this equation: (I) <code>$f(79) = 133$</code> (II) <code>$f(131) = 20$</code></p> <p>The derivative has to be zero in a minimum and a maximum, so you know two more equations: (III) <code>$f'(79) = 0$</code> (IV) <code>$f'(131) = 0$</code></p> <p>Four linear equations and four variables. Now we can solve those equations.</p> <h2>Get explicit equations</h2> <p>As a first step, we write down the equations in an explicit form. You have to know the general derivate of a cubic function: <code>$f'(x) = 3 a\cdot x^2 + 2 b \cdot x + c$</code></p> <p>(I) <code>$493039a + 6241b+79c + d = 133$</code> (II) <code>$2352637a + 17689b + 131c + d = 20$</code> (III) <code>$18723a + 158 b + c = 0$</code> (IV) <code>$51483 a + 262 b + c = 0$</code></p> <h2>Solve the equations</h2> <p>Now you have to solve the equations. I took <a href="http://www.wolframalpha.com/input/?i=493039*a%2B6241*b%2B79*c%2Bd%3D133%2C+2352637*a%2B17689*b%2B131*c%2Bd%3D20%2C+18723*a%2B158*b%2Bc%3D0%2C+51483*a%2B262*b%2Bc%3D0">Wolfram|Alpha</a>, because the numbers are really ugly. If you like to do it by hand, you have to know how to use the <a href="http://en.wikipedia.org/wiki/Gaussian_elimination">Gaussian algorithm</a>.</p> <p>Here is the exact solution:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/wolframalpha-solution-cubic-function.png"><img src="//martin-thoma.com/captions/wolframalpha-solution-cubic-function.png" alt="Exact solution of a cubic function with Wolfram|Alpah" width="511" height="70" class="size-full wp-image-42461" /></a><p class="wp-caption-text">Exact solution of a cubic function with Wolfram|Alpah</p></div> <p>And here is an approximation:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/wolframalpha-aproximate-form.png"><img src="//martin-thoma.com/captions/wolframalpha-aproximate-form.png" alt="Approximate form with Wolfram|Alpha" width="512" height="57" class="size-full wp-image-42471" /></a><p class="wp-caption-text">Approximate form with Wolfram|Alpha</p></div> <h2>The LaTeX Code</h2> <div class="highlight"><pre><code class="language-text" data-lang="text">\documentclass{article} \usepackage[pdftex,active,tightpage]{preview} \setlength\PreviewBorder{2mm} \usepackage{pgfplots} \usepackage{units} \pgfplotsset{compat=1.3}% &lt;-- moves axis labels near ticklabels % (respects tick label widths) \usepackage{tikz} \usetikzlibrary{arrows, positioning, calc, intersections, decorations.markings} \usepackage{xcolor} \definecolor{horizontalLineColor}{HTML}{008000} \definecolor{verticalLineColor}{HTML}{FF0000} \begin{document} % Define this as a command to ensure that it is same in both cases \newcommand*{\ShowIntersection}[2]{ \fill [name intersections={of=#1 and #2, name=i, total=\t}] [red, opacity=1, every node/.style={above left, black, opacity=1}] \foreach \s in {1,...,\t}{(i-\s) circle (2pt) node [above left] {\s}}; } \begin{preview} \begin{tikzpicture} \begin{axis}[ label distance=0mm, width=8cm, height=7cm, % size of the image xmin= 40, % start the diagram at this x-coordinate xmax= 180, % end the diagram at this x-coordinate ymin=60, % start the diagram at this y-coordinate ymax=170, % end the diagram at this y-coordinate ylabel=y, xlabel=x, axis lines=left, tick style={draw=none}, xticklabels={,,}, yticklabels={,,} ] \addplot[name path global=a, domain=55:161, dotted, blue, thick,samples=500, label=`$y=f(x)$`] {113/132078*x*x*x-11865/44026*x*x+1169437/44026*x-93155207/132078}; % ( 55 | 82.7344) and (161 | 156.011) are on the graph \coordinate (b) at (axis cs: 55,170); \coordinate (c) at (axis cs:161,170); \coordinate (d) at (axis cs:161,82.7344); \coordinate (e) at (axis cs:161,156.011); \coordinate (a1) at (axis cs:55,111.494); \coordinate (a2) at (axis cs:161,111.494); \draw[verticalLineColor, thick, &lt;-&gt;](a1) -- (a2); \draw[verticalLineColor,dashed](b |- 0,0) -- (b); \draw[verticalLineColor,dashed](c |- 0,0) -- (c); \draw[horizontalLineColor,dashed, thick](d -| 0,0) -- (d); \draw[horizontalLineColor,dashed, thick](e -| 0,0) -- (e); % (100 | 111.494) \coordinate (f) at (axis cs:100, 111.494); \draw[red,dashed](f |- 0,0) -- (f); \end{axis} \end{tikzpicture} \end{preview} \end{document}</code></pre></div> <h2>The result</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/08/cubic-function-intermediate-value-theorem.png"><img src="../images/2012/08/cubic-function-intermediate-value-theorem.png" alt="Cubic function intermediate value theorem - Result" width="" height="" class="size-full wp-image-42491" /></a><p class="wp-caption-text">Cubic function intermediate value theorem - Result</p></div> Konvergenz von Folgen //martin-thoma.com/konvergenz-von-folgen/ Sun, 26 Aug 2012 18:04:36 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/konvergenz-von-folgen <div class="definition">Sei `$(a_n)$` eine Folge. `$(a_n)$` hei&szlig;t <strong>konvergent</strong> `$:\Leftrightarrow \exists_{a \in \mathbb{R}} \forall_{ \varepsilon &gt; 0} \exists_{n_0 = n_0(\varepsilon) \in \mathbb{N}}: |a_n - a | &lt; \varepsilon~~~\forall n \geq n_0$`. In diesem Fall hei&szlig;t a der <strong>Grenzwert</strong> von `$(a_n)$` und man schreibt: `$\displaystyle \lim_{n \rightarrow \infty} (a_n) = a$`. Ist `$(a_n)$` nicht konvergent, so hei&szlig;t `$(a_n)$` <strong>divergent</strong>.</div> <p>Ich werde im Folgendem ein paar wichtige Hinweise geben, wie man konvergenz oder gegebenenfalls divergenz zeigen kann.</p> <h2>Wichtige Folgen</h2> <h3>Konvergent</h3> <p><code>$\displaystyle e := \lim_{n \rightarrow \infty}(1+\frac{1}{n})^n = \lim_{n \rightarrow \infty} \sum_{k=0}^n \frac{1}{n!}$</code>.</p> <p><code>$\displaystyle \lim_{n \rightarrow \infty} \frac{1}{n} = 0$</code>.</p> <p><code>$\displaystyle \lim_{n \rightarrow \infty} \sqrt[n]{c} = 1$</code>, mit <code>$c &gt; 0$</code>.</p> <p><code>$\displaystyle \lim_{n \rightarrow \infty} \sqrt[n]{n} = 1$</code>.</p> <h3>Divergent</h3> <p><code>$a_n = n$</code>.</p> <p><code>$a_n = (-1)^n$</code></p> <h2>Beschr&auml;nktheit und Monotonie</h2> <p>Wenn man zeigen kann, dass eine Folge beschränkt ist und monoton steigt oder fällt (und die Schranke in der richtigen Richtung liegt), dann konvergiert die Folge.</p> <p><strong>Beispiel:</strong></p> <div class="example">Sei `$(a_n)_{n \in \mathbb{N}}$` eine Folge und definiert durch `$a_n := 2 + \frac{1}{n}$`. 0 ist eine untere Schranke f&uuml;r `$(a_n)_{n \in \mathbb{N}}$`: `$\underbrace{2}_{\geq 0} + \underbrace{\frac{1}{n}}_{\geq 0} \Rightarrow a_n \geq 0$` `$(a_n)_{n \in \mathbb{N}}$` ist monoton fallend: Beweis von `$a_n \geq a_{n+1} ~~~ \forall_{n \in \mathbb{N}}$`: `$\begin{align} 1 &amp; \geq 0 ~~~ \forall_{n \in \mathbb{N}^+} \\ \Leftrightarrow 2n^2 + 3n + 1 &amp; \geq 2 n^2 + 3n ~~~ \forall_{n \in \mathbb{N}^+} \\ \Leftrightarrow 2n^2 + n + 2n + 1 &amp; \geq n \cdot (2n + 3) ~~~ \forall_{n \in \mathbb{N}^+} \\ \Leftrightarrow (2n + 1) \cdot (n+1) &amp; \geq n \cdot (2n + 2 + 1) ~~~ \forall_{n \in \mathbb{N}^+} \\ \Leftrightarrow \frac{2n+1}{n} &amp; \geq \frac{2 \cdot(n+1)+1}{n+1} ~~~ \forall_{n \in \mathbb{N}^+} \\ \Leftrightarrow 2 + \frac{1}{n} &amp; \geq 2 + \frac{1}{n+1} ~~~ \forall_{n \in \mathbb{N}^+} \\ \Leftrightarrow a_n &amp; \geq a_{n+1}~~~ \forall_{n \in \mathbb{N}^+} \end{align}$` `$(a_n)_{n \in \mathbb{N}}$` ist also monoton fallend und hat eine untere Schranke. `$(a_n)_{n \in \mathbb{N}}$` konvergiert also. <em>Beachte</em>: Ich habe nicht die gr&ouml;&szlig;te untere Schranke gew&auml;hlt. Hatte ich das gemacht (und bewiesen, dass es keine gr&ouml;&szlig;ere untere Schranke gibt), dann h&auml;tte ich sogar den Grenzwert bestimmt.</div> <h2>Cauchy-Folgen</h2> <p>In Banachräumen kann man auch nachweisen, dass eine Folge eine Cauchy-Folge ist um Konvergenz zu zeigen. Sie muss dazu dieser Bedingung genügen:</p> <p><code>$\forall_{\varepsilon &gt; 0} \exists_{n_0 \in \mathbb{N}}: \forall_{n,m\in\mathbb{N}, n&gt;n_0, m&gt;n_0}: |a_m- a_n| &lt; \varepsilon$</code></p> <p><strong>Beispiel:</strong> Mir fällt gerade kein Beispiel ein, bei dem man die Konvergenz schöner über das Cauchy-Kriterium zeigen kann als über die Beschränktheit / Monotonie. Falls dir eines einfällt, kannst du es ja in den Kommentar schreiben. (mit <span class="code">[latex] \lim_{n \rightarrow \infty} 123 [/latex]</span> wird es auch als LaTeX dargestellt ;-))</p> <h2>Weiteres</h2> <p>Bei Polynomen darf man den “Ausklammer-Trick” nicht vergessen: <code>$a_n = \frac{3 \cdot n^5 + 2 \cdot n^2 + 42}{1000 \cdot n^5 + n^3} = \frac{n^5}{n^5} \cdot \frac{3 + 2 \cdot \frac{1}{n^3} + 42 \cdot \frac{1}{n^5}}{1000 + \frac{1}{n^2}}= \frac{3 + 2 \cdot \frac{1}{n^3} + 42 \cdot \frac{1}{n^5}}{1000 + \frac{1}{n^2}}$</code></p> <p>Das sieht zwar deutlich schlimmer aus als vorher, ist aber besser. Wir wissen, dass <code>$\displaystyle \lim_{n \rightarrow \infty} \frac{1}{n} = 0$</code> gilt. Also gilt:</p> <p><code>$\displaystyle a_n \xrightarrow{n \rightarrow \infty} \frac{3 + 2 \cdot \overbrace{\frac{1}{n^3}}^{\rightarrow 0} + 42 \cdot \overbrace{\frac{1}{n^5}}^{\rightarrow 0}}{1000 + \underbrace{\frac{1}{n^2}}_{\rightarrow 0}} = \frac{3}{1000}$</code></p> Peg Solitaire //martin-thoma.com/peg-solitaire/ Sun, 19 Aug 2012 17:00:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/peg-solitaire <p>Solitär (auch Solitaire, Steck- oder Solohalma, Springer, Jumper, Nonnenspiel, Einsiedlerspiel) ist ein Brettspiel für eine Person. Das weitest verbreitete Spielfeld ist kreuzförmig und wird mit 32 Steinen auf 33 Felder gestartet. In der Mitte fehlt die Kugel, alle anderen 32 Felder sind besetzt.</p> <h2>Die Bezeichnungen</h2> <div style="width: 310px" class="wp-caption alignright"><a href="../images/2012/08/Peg-solitaire-board.png"><img src="//martin-thoma.com/captions/Peg-solitaire-board.png" alt="Peg Solitaire - Spielfeld" width="300" height="300" class=" wp-image-41441 " /></a><p class="wp-caption-text">Peg Solitaire - Spielfeld</p></div> <p>Dieses Brett ist hier mit den Bezeichnungen für die Felder dargestellt. Der Buchstabe bezeichnet das Feld (<strong>o</strong>ben, <strong>u</strong>nten, <strong>l</strong>inks, <strong>r</strong>echts, <strong>m</strong>ittig) und die Zahl die genaue Position, wenn man das Brett so dreht, dass das aktuelle Feld oben nur zwei Kugeln hat, sind in der obersten Zeile die Zahlen 1 und 2, in der mittigen 3, 4 und 5 und in der untersten 6, 7 und 8:</p> <h2>Die Regeln</h2> <p>Es gibt vier verschiedene Spielzüge: Der Sprung nach oben, unten, links und rechts. Es muss immer mit einer Kugel über eine andere Kugel auf ein freies Feld gesprungen werden.</p> <h2>Aufgabenstellung</h2> <p>Wie muss man ziehen, damit die letzte Kugel in der Mitte ubrig bleibt?</p> <h2>Die L&ouml;sung</h2> <p>Der erste Zug muss mit einer 2er-Kugel gemacht werden. Sagen wir, es ist o4.</p> <table> <tbody> <tr> <td>l3</td> <td>u3</td> <td>r3</td> <td>o3</td> </tr> <tr> <td>o8</td> <td>l8</td> <td>u8</td> <td>r8</td> </tr> <tr> <td>o6</td> <td>l6</td> <td>u6</td> <td>r6</td> </tr> <tr> <td>l1</td> <td>u1</td> <td>r1</td> <td>o1</td> </tr> <tr> <td>o8</td> <td>l8</td> <td>u8</td> <td>r8</td> </tr> </tbody> </table> <p>Die momentane Situation sieht folgendermaßen aus:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/08/Peg-solitaire-board-situation-1.png"><img src="//martin-thoma.com/captions/Peg-solitaire-board-situation-1.png" alt="Peg Solitaire: Board Situation" width="300" height="300" class="wp-image-41461 " /></a><p class="wp-caption-text">Peg Solitaire: Board Situation</p></div> <p>Nun kann man u1 einmal im Krei (auf r3, r5, o1, l3, l5 und dann wieder auf u1) wandern lassen. Es bleibt eine T-Form übrig:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/08/Peg-solitaire-board-situation-2.png"><img src="//martin-thoma.com/captions/Peg-solitaire-board-situation-2.png" alt="Peg Solitaire: Board Situation 2" width="300" height="300" class=" wp-image-41491 " /></a><p class="wp-caption-text">Peg Solitaire: Board Situation 2</p></div> <p>Nun muss nur noch m über l1, dann u4, r1 und schließlich l4.</p> Jordansche Normalform: 2x2 Matrizen //martin-thoma.com/jordansche-normalform-2x2-matrizen/ Fri, 17 Aug 2012 21:49:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/jordansche-normalform-2x2-matrizen <div class="info">Hier sind <span>\(2 \times 2\)</span> Beispiele zum Hauptartikel <a href="../wie-berechnet-man-die-jordansche-normalform/" title="Wie berechnet man die Jordan&rsquo;sche Normalform?">Wie berechnet man die Jordan&rsquo;sche Normalform?</a>.</div> <h2>Beispiel 1</h2> <p>Gegeben sei die Matrix <span>(A \in \mathbb{R}^{2 \times 2})</span>:</p> <div>\[A := \begin{pmatrix} 11 &amp; -4\\ 25 &amp; -9 \end{pmatrix}\]</div> <p>.</p> <h3>Jordannormalform bestimmen</h3> <p><strong>1. Charakteristisches Polynom berechnen:</strong> <span>(p_A(\lambda) = (\lambda - 1)^2)</span>.</p> <p>Daraus folgt: <span>(\lambda = 1)</span> ist einziger Eigenwert <span>(\Rightarrow)</span> 1 Jordanblock</p> <p><strong>2. Anzahl der Jordankästchen bestimmen:</strong></p> <div>\[ \begin{align} \dim E_{1} &amp;= \dim \text{Kern}(A -1 \cdot I) \\ &amp;= \dim \text{Kern} \begin{pmatrix} 10 &amp; -4\\ 25 &amp; -10 \end{pmatrix}\\ &amp;= \dim \text{Kern} \begin{pmatrix} 10 &amp; -4\\ 0 &amp; 0 \end{pmatrix}\\ &amp;= \dim \left [ \begin{pmatrix}2\\5\end{pmatrix} \right ] \\ &amp;= 1 \end{align}\]</div> <p><span>(\Rightarrow)</span> es gibt genau 1 Jordankästchen in diesem Jordanblock.</p> <div>\[\Rightarrow J = \begin{pmatrix}1 &amp; 1\\ 0 &amp; 1 \end{pmatrix}\]</div> <p>.</p> <h3>Basiswechselmatrix bestimmen</h3> <p><strong>Basisvektoren für den Eigenwert 1 bestimmen:</strong></p> <div>\[\Omega = \Phi_{| H_\lambda} - \lambda \cdot id = \begin{pmatrix} 10 &amp; - 4\\ 25 &amp; -10 \end{pmatrix} \]</div> <p>,</p> <div>\[K_1 = \text{Kern } \Omega^1 = \left [ \begin{pmatrix}2 \\ 5 \end{pmatrix} \right ]\]</div> <div>\[K_2 = \text{Kern } \Omega^2 = \text{Kern } (\begin{pmatrix}10 &amp; -4\\ 25 &amp; -10 \end{pmatrix} \cdot \begin{pmatrix}10 &amp; -4\\ 25 &amp; -10 \end{pmatrix}) = \text{Kern } (\begin{pmatrix}0 &amp; 0\\ 0 &amp; 0 \end{pmatrix}) = \left[ \begin{pmatrix}1 \\ 0 \end{pmatrix}, \begin{pmatrix}0 \\ 1 \end{pmatrix} \right]\]</div> <div>\[K_2 \stackrel{!}{=} U_1 \oplus K_1 \Rightarrow \left [ \begin{pmatrix} 1 \\ 0 \end{pmatrix} \right ] ~~~ U_0 = K_1\]</div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/08/jordan-normal-form-scheme-small.png"><img src="../images/2012/08/jordan-normal-form-scheme-small.png" alt="Schema zum finden der Basiswechselmatrix" width="" height="" class="size-full wp-image-40961" /></a><p class="wp-caption-text">Schema zum finden der Basiswechselmatrix</p></div> <p>Wähle &lt;div&gt;[b_1^1 \in U_1: b_1^1 = \begin{pmatrix}1 \0 \end{pmatrix} \Rightarrow \Omega(b_1^1) = \begin{pmatrix}10 \ 25 \end{pmatrix}]&lt;/div&gt;</p> <div>\[\Rightarrow S = \begin{pmatrix} 10 &amp; 1 \\ 25 &amp; 0 \end{pmatrix}\]</div> <div>\[\Rightarrow S^{-1} = \begin{pmatrix} 0 &amp; \frac{1}{25} \\ 1 &amp; -\frac{2}{5} \end{pmatrix}\]</div> <div>\[A = S \cdot J \cdot S^{-1}\]</div> <div>\[\Leftrightarrow \begin{pmatrix} 11 &amp; -4\\ 25 &amp; -9 \end{pmatrix} = \begin{pmatrix} 10 &amp; 1 \\ 25 &amp; 0 \end{pmatrix} \cdot \begin{pmatrix}1 &amp; 1\\ 0 &amp; 1 \end{pmatrix} \cdot \begin{pmatrix} 0 &amp; \frac{1}{25} \\ 1 &amp; -\frac{2}{5} \end{pmatrix}\]</div> <h2>Beispiel 2</h2> <p>Gegeben sei die Matrix <span>(A \in \mathbb{R}^{2 \times 2})</span>:</p> <div>\[A := \begin{pmatrix} 1 &amp; 2\\ 3 &amp; 6 \end{pmatrix}\]</div> <p>.</p> <h3>Jordannormalform bestimmen</h3> <p><strong>1. Charakteristisches Polynom berechnen:</strong></p> <div>\[p_A(\lambda) = \det \begin{pmatrix} 1 -\lambda &amp; 2\\ 3 &amp; 6 - \lambda \end{pmatrix} = (1- \lambda) \cdot (6 - \lambda) - 6 = 6-6\lambda-\lambda+\lambda^2-6=\lambda^2-7\lambda = \lambda \cdot (\lambda - 7)\]</div> <p>Daraus folgt: 0 und 1 sind Eigenwerte. Sie haben jeweils die algebraischen Vielfachheit 1. Daraus folgt: Die Jordansche Normalform hat genau zwei Jordanblöcke, die beide die Größe 1x1 haben. Daraus folgt: Beide Jordanblöcke haben genau ein Jordankästchen der Größe 1x1. Daraus folgt: Die Jordansche Normalform der Matrix ist:</p> <div>\[J = \begin{pmatrix} 0 &amp; 0\\ 0 &amp; 7 \end{pmatrix}\]</div> <h3>Basiswechselmatrix bestimmen</h3> <p><strong>Basisvektoren für den Eigenwert 0 bestimmen:</strong></p> <div>\[K_1 = \text{Kern }(A- 0 \cdot E) = \text{Kern } \begin{pmatrix} 1 &amp; 2\\ 3 &amp; 6 \end{pmatrix} = \left [ \begin{pmatrix}2 \\ -1 \end{pmatrix} \right ] \]</div> <p><strong>Basisvektoren für den Eigenwert 7 bestimmen:</strong></p> <div>\[K_1 = \text{Kern }(A- 7 \cdot E) = \text{Kern } \begin{pmatrix} -6 &amp; 2\\ 3 &amp; -1 \end{pmatrix} = \text{Kern } \begin{pmatrix} 1 &amp; -\frac{1}{3}\\ 0 &amp; 0 \end{pmatrix} = \left [ \begin{pmatrix}1 \\ 3 \end{pmatrix} \right ] \]</div> <p><strong>Zusammensetzen:</strong></p> <div>\[S = \begin{pmatrix}2 &amp; 1 \\ -1 &amp; 3 \end{pmatrix}\]</div> <div>\[S^{-1} = \frac{1}{7} \cdot \begin{pmatrix}3 &amp; -1 \\ 1 &amp; 2 \end{pmatrix}\]</div> <h3>Anmerkung</h3> <p>Man hätte übrigens jeden Vektor aus <span>(\left [ \begin{pmatrix}2 \ -1 \end{pmatrix} \right ] )</span> nehmen können. Angenommen, man hätte den Vektor <span>(\begin{pmatrix}-14 \ 7 \end{pmatrix})</span> gewählt:</p> <div>\[S = \begin{pmatrix}-14 &amp; 1 \\ 7 &amp; 3 \end{pmatrix}\]</div> <div>\[S^{-1} = \frac{1}{49} \cdot \begin{pmatrix}-3 &amp; 1 \\ 7 &amp; 14 \end{pmatrix}\]</div> <p>Das gleiche gilt natürlich für jeden anderen gewählten Vektor. Die inverse Matrix ändert sich selbstverständlich, jedoch nicht die Jordansche Normalform oder die ursprüngliche Matrix.</p> Wie berechnet man die Jordan'sche Normalform? //martin-thoma.com/wie-berechnet-man-die-jordansche-normalform/ Fri, 17 Aug 2012 12:59:27 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-berechnet-man-die-jordansche-normalform <p>Dieser Artikel beschreibt, wie die Jordansche Normalform einer Matrix sowie die dazugehörige Basiswechselmatrix gefunden werden kann. Dabei wird hier eine Jordansche Normalform erzeugt, bei der die 1er auf der oberen Nebendiagonale sind und die größten Jordankästchen zuerst kommen.</p> <p>Ich werde hier nicht erklären, warum es so funktioniert.</p> <p>Hier sind zwei <a href="../jordansche-normalform-2x2-matrizen/" title="Jordansche Normalform: 2&times;2 Matrizen">Beispiele mit 2x2-Matrizen</a> und <a href="../jordansche-normalform-4x4-matrizen/" title="Jordansche Normalform: 4&times;4 Matrizen">Beispiele mit 4x4-Matrizen</a>.</p> <p>Gegeben sei eine Matrix <span>(A \in \mathbb{C}^{n \times n})</span>.</p> <h2>Berechnung der Jordanschen Normalform</h2> <h3>Charakteristisches Polynom bestimmen</h3> <p>Als ersten Schritt muss man das charakteristische Polynom <span>(p_A(\lambda))</span> der Matrix <span>(A)</span> bestimmen.</p> <p>→ <a href="../wie-berechnet-man-das-charakteristische-polynom/" title="Wie berechnet man das charakteristische Polynom?">Wie berechnet man das charakteristische Polynom?</a></p> <h3>Zerlegung in Linearfaktoren</h3> <p>Die Zerlegung des charakteristischen Polynoms <span>(p_A(\lambda))</span> in Linearfaktoren kann ziemlich schwer sein. Dafür muss man unbedingt die Mitternachtsformel <span>(\lambda_{1,2} = \frac{-b \pm \sqrt{b^2 - 4ac}}{2a})</span> können und eventuell wissen, wie eine <a href="http://de.wikipedia.org/wiki/Polynomdivision#Manueller_Ablauf">Polynomdivision</a> funktioniert. Eventuell muss man dazu auch Nullstellen erraten. Wenn es ums raten geht, würde ich folgendes ausprobieren: 0, 1, -1, 2, -2, 3, -3.</p> <p>Sobald man diese Zerlegung hat, kann man die Eigenwerte und die algebraische Vielfachheit der Eigenwerte direkt ablesen. Die Eigenwerte stehen in der Jordanmatrix auf der Diagonalen. Die algebraische Vielfachheit entspricht der Seitenlänge des quadratischen Jordanblocks.</p> <h3>Anzahl der Jordankästchen bestimmen</h3> <p>Jeder Eigenwert hat genau einen Jordanblock. Jeder Jordanblock hat wiederum Jordankästchen. Das sieht so aus:</p> <p><span>( J = \left( \begin{array}{*4{c}} A_{\lambda_1} &amp; &amp; &amp; 0<br /> &amp; A_{\lambda_2} &amp; &amp; <br /> &amp; &amp; \ddots &amp; <br /> 0 &amp; &amp; &amp; A_{\lambda_k} \end{array} \right))</span></p> <p><span>(A_{\lambda_i})</span> sind die Jordanblöcke zu den Eigenwerten <span>(\lambda_i)</span>.</p> <p>Die Einzelnen Jordanblöcke schauen etwa so aus:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/08/jordan-normal-form-block.png"><img src="../images/2012/08/jordan-normal-form-block.png" alt="Einzelner Jordanblock mit zwei hervorgehobenen Jordankästchen" width="" height="" class="size-full wp-image-40381" /></a><p class="wp-caption-text">Einzelner Jordanblock mit zwei hervorgehobenen Jordankästchen</p></div> <p>Jedes Jordankästchen ist quadratisch, hat auf der Diagonalen den Eigenwert und auf der oberen Nebendiagonale 1er. Sonst sind nur 0er im Jordankästchen. Außerhalb der Jordankästchen sind im Jordanblock nur 0er. Insbesondere können also auf der oberen Nebendiagonalen des Jordanblocks 0er stehen!</p> <p>Es gilt: <span>(\text{geometrische Vielfachheit des Eigenwertes } \lambda := \dim E_\lambda \leq \text{algebraische Vielfachheit des Eigenwertes } \lambda)</span> <span>(\dim E_\lambda = \dim \text{Kern}(A - \lambda \cdot I) = \text{Anzahl der Jordankästchen im Jordanblock zu } \lambda)</span></p> <p>→ <a href="../wie-bestimme-ich-den-kern-einer-linearen-abbildung/" title="Wie bestimme ich den Kern einer linearen Abbildung?">Wie bestimme ich den Kern einer linearen Abbildung?</a></p> <p>Außerdem gilt: Die Größe des größten Jordankästchens zum Eigenwert <span>(\lambda_i)</span> ist gleich der Potenz, mit der der Linearfaktor <span>((x-\lambda_i))</span> im Minimalpolynom (leider NICHT das charakteristische Polynom ☹ ) vorkommt.</p> <p>Nun kann man häufig schon schlussfolgern, welche Größe die einzelnen Jordankästchen haben. Zusätzlich haben ähnliche Matrizen die gleiche Spur, die gleiche Determinante und den gleichen Rang. Das könnte helfen um “falsche” Jordanmatrizen auszuschließen.</p> <p>Damit ist die Jordansche Normalform der Matrix häufig schon bestimmt.</p> <h3>Größe der Jordankästchen bestimmen</h3> <p>Sei <span>(\Omega = \Phi - \lambda \cdot id)</span> und <span>(K_k = \text{Kern } ((\Omega)^k))</span></p> <p>Man wähle <span>(q \in N^+)</span> so, dass <span>(\dim K_q = \dim K_{q+1} = \dim K_{q+2} = … = \dim V)</span> und q minimal. Dann gilt: q ist die länge des größten Jordankästchens in dem Jordanblock (und außerdem der Exponent im Minimalpolynom zum betrachteten Eigenwert <span>(\lambda)</span>).</p> <p>Es sei <span>(a_0 = \dim K_0 = 0, a_1 = \dim K_1, a_i = \dim K_i)</span> mit <span>(i \in 0, …, q)</span>.</p> <p>Es gilt:</p> <ul> <li>Anzahl der Kästchen der Größe <span>\(1 \times 1\)</span>: <span>\(2 \cdot a_1 - a_0 - a_2\)</span></li> <li>Anzahl der Kästchen der Größe <span>\(2 \times 2\)</span>: <span>\(2 \cdot a_2 - a_1 - a_3\)</span></li> <li>Anzahl der Kästchen der Größe <span>\(3 \times 3\)</span>: <span>\(2 \cdot a_3 - a_2 - a_4\)</span></li> <li>Anzahl der Kästchen der Größe <span>\(i \times i\)</span>: <span>\(2 \cdot a_i - a_{i-1} - a_{i+1}\)</span></li> </ul> <h2>Berechnung der Basiswechselmatrix</h2> <p>Die Basiswechselmatrix wird manchmal auch Transformationsmatrix genannt. Es ist die invertierbare Matrix S, für die gilt: <span>(A = S \cdot J \cdot S^{-1})</span></p> <h3>Kerne bestimmen</h3> <p>Bestimme <span>(K_1, K_2, K_3, … , K_q)</span>, wobei <span>(\dim K_{q-1} &lt; \dim K_q = \dim K_{q+1} = \dim K_{q+2} …)</span> gilt. Man kann also bei <span>(K_q)</span> aufhören.</p> <p>Für jedes <span>(K_k)</span> mit <span>(k \in 1, …, q)</span> bestimmt man eine möglichst einfache Basis.</p> <h3>Zusammensetzen</h3> <p>An dieser Stelle sollte man wissen, wie groß die Jordankästchen sind.</p> <p>Für ein Jordankästchen der Größe <span>(i)</span> wählt man einen Basisvektor <span>(v_i)</span> aus <span>(K_i)</span>, der jedoch nicht in <span>(K_{i-1})</span> liegt. Die restlichen <span>(i-1)</span> Vektoren für dieses Kästchen erhält man, indem man die Abbildungsmatrix von <span>(\Omega^{j})</span>, mit <span>(j = 1, …, i-1)</span>, mit <span>(v_i)</span> multipliziert.</p> <p>Also: <span>(v_j = (A - \lambda \cdot E)^{i-j})</span> mit <span>(j = 1, …, i)</span></p> <p>Die Vektoren <span>(v_j)</span> schreibt man mit aufsteigenden Indizes in die geordete Basis. Beachte: Man wählt nur den Vektor <span>(v_i)</span>, alle anderen Vektoren für dieses Kästchen sind dadurch festgelegt! Außerdem schreibt man <span>(v_i)</span> erst am Ende in die Basis!</p> <h3>Inverse Matrix bestimmen</h3> <p>Sobald man <span>(S)</span> bestimmt hat, muss man nur noch das Inverse davon bestimmen: → <a href="../wie-bestimme-ich-das-inverse-einer-matrix/" title="Wie bestimme ich das Inverse einer Matrix?">Wie bestimme ich das Inverse einer Matrix?</a></p> <h2 id="interessante-eigenschaften-der-jnf">Interessante Eigenschaften der JNF</h2> <p>Im Zusammenhang mit der JNF (und einigen Klausuraufgaben) sind mir ein paar erwähnenswerte Eigenschaften aufgefallen:</p> <p><strong>Die Anzahl der Jordankästchen zum Eigenwert <span>(\lambda = 0)</span> ist <span>(n - \text{Rang}(A))</span>.</strong><br /> <em>Begründung</em>: Die Anzahl der Jordankästchen zum Eigenwert <span>(\lambda)</span> ist gleich der Dimension des Eigenraumes von <span>(\lambda)</span>. Der Eigenraum zum Eigenwert 0 hat die besonderheit, dass es der Kern ist. Nach der Dimensionsformel gilt: <span>(\dim \text{Kern}(\Phi) + \dim \text{Bild}(\Phi) = n = \dim \text{Kern} + \text{ Rang}(A_\Phi))</span>.</p> Java Puzzle #10: Multiple Interfaces //martin-thoma.com/java-puzzle-10-multiple-interfaces/ Thu, 16 Aug 2012 17:00:25 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-10-multiple-interfaces <p>You have to following source code:</p> <p><strong>A.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">interface</span> <span class="nc">A</span> <span class="o">{</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">methodA</span><span class="o">(</span><span class="kt">double</span> <span class="n">a</span><span class="o">,</span> <span class="kt">int</span> <span class="n">b</span><span class="o">,</span> <span class="kt">char</span> <span class="n">c</span><span class="o">);</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">methodB</span><span class="o">();</span> <span class="o">}</span></code></pre></div> <p><strong>B.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">interface</span> <span class="nc">B</span> <span class="o">{</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">methodB</span><span class="o">();</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">methodC</span><span class="o">();</span> <span class="o">}</span></code></pre></div> <p><strong>test.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="kd">implements</span> <span class="n">A</span><span class="o">,</span> <span class="n">B</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">test</span> <span class="n">t</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">test</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">t</span><span class="o">.</span><span class="na">methodA</span><span class="o">(</span><span class="mi">1</span><span class="o">,</span> <span class="mi">2</span><span class="o">,</span> <span class="sc">&#39;3&#39;</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">t</span><span class="o">.</span><span class="na">methodB</span><span class="o">());</span> <span class="n">t</span><span class="o">.</span><span class="na">methodC</span><span class="o">();</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">methodA</span><span class="o">(</span><span class="kt">double</span> <span class="n">a</span><span class="o">,</span> <span class="kt">int</span> <span class="n">b</span><span class="o">,</span> <span class="kt">char</span> <span class="n">c</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">42</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">int</span> <span class="nf">methodB</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">1337</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">methodC</span><span class="o">()</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;methodC executed.&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>What is the output? Does it compile? Is there a <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/RuntimeException.html">RuntimeException</a>?</p> <p>. . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">42 1337 methodC executed.</code></pre></div> <h2>Explanation</h2> <p>If you use an Interface, it simply means you have to implement some methods. If more than one Interface forces you to implement the method, you still have to implement it only once. It just works fine.</p> Wie bestimme ich den Kern einer linearen Abbildung? //martin-thoma.com/wie-bestimme-ich-den-kern-einer-linearen-abbildung/ Thu, 16 Aug 2012 15:54:15 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-bestimme-ich-den-kern-einer-linearen-abbildung <h2>Definition</h2> <p>Der Kern einer linearen Abbildung ist eine Menge von Vektoren. In diesem Artikel erkläre ich kurz und bündig, wie man den Kern einer linearen Abbildung bestimmt.</p> <div class="definition">Sei `$\Phi: V \rightarrow W$` eine lineare Abbildung. Der <strong>Kern</strong> von `$\Phi$` ist die Menge aller Vektoren von V, die durch `$\Phi$` auf den Nullvektor `$0 \in W$` abgebildet werden, also: `$\text{Kern } \Phi := \{v \in V | \Phi(v) = 0\}$`</div> <h2>Vorgehen</h2> <p>Jede lineare Abbildung <code>$\Phi$</code> lässt sich in dieser Form beschreiben:</p> <p><code>$\Phi: V \rightarrow W$</code> mit <code>$\dim V = m$</code> und <code>$\dim W = n$</code> <code>$\Phi(x) = A \cdot x, ~~~ A \in R^{n \times m}, x \in V$</code></p> <p>Also muss man, um den Kern von <code>$\Phi$</code> zu bestimmen, nur das folgende homogene Gleichungssystem nach x auflösen: <code>$A \cdot x = 0$</code></p> <table> <tbody> <tr> <td>In Wolfram</td> <td>Alpha benötigt man dafür übrigens das Schlüsselwort <code>null space</code>. Hier ist <a href="http://www.wolframalpha.com/input/?i=nullspace+%7B%7B-1%2C-1%2C-2%2C-2%2C-1%7D%2C%7B3%2C0%2C2%2C1%2C2%7D%2C%7B0%2C1%2C1%2C1%2C0%7D%2C%7B-1%2C-1%2C-2%2C-2%2C-1%7D%2C%7B2%2C1%2C3%2C3%2C2%7D%7D">Beispiel #2 in Wolfram</a></td> <td>Alpha&lt;/a&gt;.</td> </tr> </tbody> </table> <h2>Beispiel #1</h2> <h3>Aufgabenstellung</h3> <p>Sei <code>$A \in \mathbb{R}^{3 \times 3}$</code> und definiert als</p> <p><code>$A := \begin{pmatrix} 1 &amp; 2 &amp; 3\\ 4 &amp; 5 &amp; 6\\ 7 &amp; 8 &amp; 9 \end{pmatrix}$</code></p> <p>Sei <code>$\Phi: \mathbb{R}^3 \rightarrow \mathbb{R}^3$</code> eine lineare Abbildung und definiert als</p> <p><code>$\Phi(x) := A \cdot x$</code>.</p> <p>Was ist der Kern von <code>$\Phi$</code>?</p> <h3>Rechnung</h3> <p><code>$ \begin{pmatrix} 1 &amp; 2 &amp; 3\\ 4 &amp; 5 &amp; 6\\ 7 &amp; 8 &amp; 9 \end{pmatrix} \leadsto \begin{pmatrix} 1 &amp; 2 &amp; 3\\ 0 &amp; -3 &amp; -6\\ 0 &amp; -6 &amp; -12 \end{pmatrix} \leadsto \begin{pmatrix} 1 &amp; 2 &amp; 3\\ 0 &amp; 1 &amp; 2\\ 0 &amp; 1 &amp; 2 \end{pmatrix} \leadsto \begin{pmatrix} 1 &amp; 0 &amp; -1\\ 0 &amp; 1 &amp; 2\\ 0 &amp; 0 &amp; 0 \end{pmatrix} $</code></p> <p>Man sieht direkt, dass die Matrix den Rang 2 hat. Also muss der Lösungsraum 1-dimensional sein. Mit dem -1-Trick kommt nam auf den Lösungsraum:</p> <p><code>$\mathcal{L} = \left [ \begin{pmatrix} -1\\ 2\\ -1 \end{pmatrix} \right ]$</code></p> <p>Also:</p> <p><code>$\text{Kern } \Phi = \left [ \begin{pmatrix} -1\\ 2\\ -1 \end{pmatrix} \right ]$</code></p> <h2>Beispiel #2</h2> <h3>Aufgabenstellung</h3> <p>Sei <code>$A \in \mathbb{R}^{5 \times 5}$</code> und definiert als</p> <p><code>$A := \begin{pmatrix} -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 3 &amp; 0 &amp; 2 &amp; 1 &amp; 2\\ 0 &amp; 1 &amp; 1 &amp; 1 &amp; 0\\ -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 2 &amp; 1 &amp; 3 &amp; 3 &amp; 2 \end{pmatrix}$</code></p> <p>Sei <code>$\varphi: \mathbb{R}^5 \rightarrow \mathbb{R}^5$</code> eine lineare Abbildung und definiert als</p> <p><code>$\varphi(x) := A \cdot x$</code>.</p> <p>Was ist der Kern von <code>$\varphi$</code>?</p> <h3>Rechnung</h3> <p><code>$\begin{pmatrix} -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 3 &amp; 0 &amp; 2 &amp; 1 &amp; 2\\ 0 &amp; 1 &amp; 1 &amp; 1 &amp; 0\\ -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 2 &amp; 1 &amp; 3 &amp; 3 &amp; 2 \end{pmatrix} \cdot \begin{pmatrix} x_1 \\ x_2 \\ x_3 \\ x_4 \\ x_5 \end{pmatrix} = \begin{pmatrix} 0 \\ 0 \\ 0 \\ 0 \\ 0 \end{pmatrix}$</code></p> <p><code>$\leadsto \begin{pmatrix} -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 3 &amp; 0 &amp; 2 &amp; 1 &amp; 2\\ 0 &amp; 1 &amp; 1 &amp; 1 &amp; 0\\ -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 2 &amp; 1 &amp; 3 &amp; 3 &amp; 2 \end{pmatrix} \leadsto \begin{pmatrix} -1 &amp; -1 &amp; -2 &amp; -2 &amp; -1\\ 0 &amp; -3 &amp; -4 &amp; -5 &amp; -4\\ 0 &amp; 1 &amp; 1 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; -1 &amp; -1 &amp; -1 &amp; 0 \end{pmatrix}$</code></p> <p><code>$\leadsto \begin{pmatrix} 1 &amp; 1 &amp; 2 &amp; 2 &amp; 1\\ 0 &amp; 1 &amp; 1 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; -1 &amp; -2 &amp; -1\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix} \leadsto \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; -1 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; -1 &amp; -1\\ 0 &amp; 0 &amp; 1 &amp; 2 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0\\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0 \end{pmatrix}$</code></p> <p>Die Matrix hat Rang 3, daraus folgt, dass die Dimension des Lösungsraumes 2 ist. Wieder über den -1-Trick kann man den Lösungsraum direkt ablesen:</p> <p><code>$\mathcal{L} = \left [ \begin{pmatrix} -1\\ -1\\ 2\\ -1\\ 0 \end{pmatrix}, \begin{pmatrix} 0\\ -1\\ 1\\ 0\\ -1 \end{pmatrix} \right ] = \text{Kern} \varphi $</code></p> Der Kaiser von China und der Reis //martin-thoma.com/der-kaiser-von-china-und-der-reis/ Wed, 15 Aug 2012 17:00:54 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/der-kaiser-von-china-und-der-reis <p><a href="../images/2012/08/chessboard-rice.png"><img src="../images/2012/08/chessboard-rice.png" alt="" title="Schachbrett mit Reis" width="191" height="128" class="alignright size-full wp-image-46151" /></a></p> <h2>Aufgabenstellung</h2> <p>Der Kaiser von China spielt mit einem Bauern Schach. Nachdem er das Spiel verloren hat, ist der Kaiser großzügig und will dem Bauern jeden Wunsch erfüllen. Der Bauer gibt sich bescheiden und verlangt für das erste Schachfeld ein Reiskorn, für das zweite zwei Reiskörner, usw.</p> <p>Allgemein formuliert verlangt er für jedes Schachfeld doppelt so viele Reiskörner wie für das Vorhergehende.</p> <p>Wieviel Reis muss der Kaiser von China abtreten?</p> <h2>L&ouml;sung</h2> <p>Ein Schachbrett hat <code>$8 \cdot 8 = 64$</code> Felder. Für das <code>$i$</code>-te Feld, <code>$1 \le i \le 64$</code>, muss der Kaiser <code>$2^{i-1}$</code> Reiskörner abgeben. Insgesamt muss er also <code>$\sum_{i=1}^{64} 2^{i-1}$</code> Reiskörner abgeben. Das sind <code>$2^{64} - 1 = 18446744073709551615 \approx 1{,}84 \cdot 10^{19}$</code> Reiskörner.</p> <h2>Vergleiche</h2> <p>Wie viel sind 18.446.744.073.709.551.615 Reiskörner?</p> <h3>Erdabdeckung</h3> <p>Würde man die Erde gleichmäßig mit Reiskörnern abdecken, wie hoch wäre diese Schicht?</p> <p>Die Erde hat eine Oberfläche von ca. 510 Millionen <code>$\text{km}^2$</code>, ein Basmati-Reiskorn ist ca 6,5 mm lang, hat einen Durchmesser von ca. 1,5 mm und hat vereinfacht eine Kreiszylinderform.</p> <p>Daraus ergibt sich folgende Gleichung, bei der <code>$x$</code> die Höhe der Reisschicht ist:</p> <p><code>$ \begin{align} x \cdot A_{Erde} &amp;= (2^{64}-1) \cdot 6,5\text{mm} \cdot (1,5\text{mm})^2 \cdot \pi \\ x &amp;= \frac{(2^{64}-1) \cdot 6,5\text{mm} \cdot (1,5\text{mm})^2 \cdot \pi}{A_{Erde}} \\ x &amp;= \frac{(2^{64}-1) \cdot 45,9458\text{mm}^3}{510 \cdot 10^6 \cdot 10^{12} \text{mm}^2} \\ x &amp;= \frac{8,47550 \cdot 10^{20} \text{mm}^3}{510 \cdot 10^{18} \text{mm}^2} \\ x &amp;= 1,662\text{mm} \end{align} $</code></p> <p>Die Erde könnte also komplett mit ca. 1,662 mm Reis, also etwas mehr als einem Reiskorn, bedeckt werden.</p> <h3>Reispackungen</h3> <p>Den vorhergehenden Vergleich finde ich noch etwas unpraktisch. Wieviele Reispackungen wären das?</p> <p>Eine handelsübliche Packung Reis beinhaltet ca. 1 kg Reis. Ein Reiskorn wiegt ca. 65 mg.</p> <p><code>$ \begin{align} x &amp;:= \text{Reispackungen} \\ x \cdot 1\text{kg} &amp;= 65\text{mg} \cdot (2^{64}-1) \\ x \cdot 10^6\text{mg} &amp;= 1199038364791120854975\text{mg} \\ x &amp;\approx 1,2 \cdot 10^{15} \end{align} $</code></p> <h3>Reispackungen pro Person</h3> <p>Auch <code>$1,2 \cdot 10^{15}$</code> ist noch zu groß, um sich etwas darunter vorstellen zu können. Wie viele Reispackungen wären das pro Person auf der Erde?</p> <p><code>$ \begin{align} x &amp;:= \text{Reispackungen pro Mensch} \\ x &amp;= \frac{1,2 \cdot 10^{15}}{6,93 \cdot 10^9} \\ x &amp;\approx 1,7 \cdot 10^5 \end{align} $</code> Jeder Mensch würde also 170.000 Packungen Reis von Kaiser von China bekommen. Um den täglichen Kalorienbedarf zu decken werden ca. 1,1 kg Reis benötigt. Es könnten also alle Menschen der Erde ca. 154.545 Tage, das sind über 423 Jahre, ernährt werden!</p> <h3>Marktwert</h3> <p>Reis kostet auf dem Weltmarkt ca. 600 US-Dollar pro metrischer Tonne (<a href="http://www.markt-daten.de/charts/imf/imf014.htm">Quelle</a>).</p> <p><code>$ \begin{align} x &amp;:= \text{Marktwert} \\ x &amp;= \frac{1,2 \cdot 10^{15}}{1000} \cdot 600 \text{ US-Dollar}\\ x &amp;= 720000000000000 \end{align} $</code></p> <p>Der Reis hätte also einen Marktwert von 720 Billionen US-Dollar.</p> <p>Zum Vergleich: Das BIP der gesamten Welt, also die Summe der Werte aller Güter und Dienstleistung, lag 2007 bei ca. 54 Billionen US-Dollar (<a href="http://www.bpb.de/wissen/I6PFEV,0,WeltBruttoinlandsprodukt.html">Quelle</a>).</p> Klausur Analysis I und II //martin-thoma.com/klausur-analysis-i-und-ii/ Tue, 14 Aug 2012 17:13:24 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/klausur-analysis-i-und-ii <div class="info">Dieser Artikel richtet sich vor allem an Studenten, die im Sommersemester 2012 bei Herrn Prof. Dr. Schmoeger am KIT die Klausur &uuml;ber Analysis schreiben werden.</div> <h2>Vorbereitung</h2> <h3>Analysis I</h3> <h4>Themen</h4> <ul> <li><strong>Definitionen und Beispiele</strong>: Beschr&auml;nktheit, injektiv, surjektiv, bijektiv, endlich, unendlich, abz&auml;hlbar, &uuml;berabz&auml;hlbar</li> <li><a href="http://de.wikipedia.org/wiki/Bernoullische_Ungleichung">Bernoullische Ungleichung</a>: Ist `$x \geq -1$`, so gilt: `$(1+x)^n \geq 1 + nx~~~\forall n \in \mathbb{N}^+$`</li> <li><a href="http://de.wikipedia.org/wiki/Binomischer_Lehrsatz">Binomischer Lehrsatz</a>: `$(a+b)^n = \sum_{k=0}^{n} \binom{n}{k} a^{n-k} b^k$`</li> <li><strong>Folgen</strong>: <ul> <li><a href="../konvergenz-von-folgen/">Konvergenz</a></li> <li>(strenge) Monotonie</li> <li>Grenzwert</li> <li>Divergenz</li> <li>Konvergenzkriterien: <a href="http://de.wikipedia.org/wiki/Wurzelkriterium">Wurzelkriterium</a>, <a href="http://de.wikipedia.org/wiki/Leibniz-Kriterium">Leibniz-Kriterium</a>, <a href="http://de.wikipedia.org/wiki/Cauchykriterium">Cauchy-Kriterium</a>, <a href="http://de.wikipedia.org/wiki/Majorantenkriterium">Majorantenkriterium</a>, Minorantenkriterium, <a href="http://de.wikipedia.org/wiki/Quotientenkriterium">Quotientenkriterium</a></li> <li><a href="http://de.wikipedia.org/wiki/Eulersche_Zahl">Eulersche Zahl</a>: `$\displaystyle e := \lim_{n \rightarrow \infty}(1+\frac{1}{n})^n = \lim_{n \rightarrow \infty} \sum_{k=0}^n \frac{1}{n!}$`</li> <li>H&auml;ufungswert vs. H&auml;ufungspunkt: &rarr; <a href="http://de.wikipedia.org/wiki/Diskussion:H%C3%A4ufungspunkt#H.C3.A4ufungspunkt_und_H.C3.A4ufungswert">Diskussion</a> <ul> <li>Oberer- und unterer Limes</li> </ul> </li> </ul> </li> <li>Unendliche Reihen</li> <li><a href="http://de.wikipedia.org/wiki/Potenzreihe">Potenzreihe</a></li> <li>Stetigkeit</li> <li><a href="http://de.wikipedia.org/wiki/Gleichm%C3%A4%C3%9Fige_Stetigkeit">Gleichm&auml;&szlig;ige Stetigkeit</a>: Definition, Beispiele</li> <li>H&ouml;here Ableitungen</li> <li><strong>Integrale</strong> <ul> <li>Riemann-Integral</li> <li>Uneigentliche Integrale</li> <li><a href="http://de.wikipedia.org/wiki/Riemann-Stieltjes-Integral">Riemann-Stieltjes-Integral</a></li> <li>Partielle Integration<br />`$\int_a^b f'(x)\cdot g(x)\,\mathrm{d}x = [f(x)\cdot g(x)]_{a}^{b} - \int_a^b f(x)\cdot g'(x)\,\mathrm{d}x.$`</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Beschr%C3%A4nkte_Variation">Funktionen beschr&auml;nkter Variation</a> <ul> <li>Totalvariation</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Zwischenwertsatz">Zwischenwertsatz</a></li> <li><a href="http://de.wikipedia.org/wiki/Mittelwertsatz_der_Differentialrechnung">Mittelwertsatz</a></li> </ul> <h4>Aufgabenstellungen</h4> <ul> <li>Wahr/Falsch-Ankreuzaufgabe</li> <li>Grenzwert von Folgen bestimmen</li> <li>Konvergenzradius von Potenzreihen bestimmen</li> <li>Zeige, dass eine Funktion stetig ist. Ansatz: <br /> `$f \text{ ist stetig} :\Leftrightarrow \forall \varepsilon &gt; 0 \ \exists \delta \ \forall x, z \text{ mit } |x - z| &lt; \delta: |f(x)- f(z)| &lt; \varepsilon$`</li> <li>Zeige, dass eine Funktion differenzierbar ist. Ansatz: h-Methode<br /> `$\displaystyle \lim_{h \rightarrow 0} \frac{f(x_0+h)-f(x_0)}{h}$`</li> <li>Funktionenfolgen auf punktweise und gleichm&auml;&szlig;ige Konvergenz untersuchen</li> <li>Allgemeine Eigenschaften der e-Funktion und der Winkelfunktionen</li> <li>Wert von Integralen bestimmen</li> </ul> <h3>Analysis II</h3> <h4>Themen und Schlagworte</h4> <ul> <li>Quadratische Formen</li> <li>Umkehrsatz</li> <li>Implizit definierte Funktionen</li> <li>Wege <ul> <li>Wegl&auml;nge: `$L(\gamma) = \int \| \gamma'(t) \| dt$`</li> <li>Wegintegral: `$\int_\gamma f(x, y, z) d(x,y,z) = \int f(\gamma(t)) \cdot \gamma'(t) dt$`</li> </ul> </li> <li>Fixpunkte, Fixpunktsatz von Banach</li> <li><a href="http://de.wikipedia.org/wiki/Jacobi-Matrix">Jacobi-Matrix</a></li> <li>Extremwerte <ul> <li>... unter Nebenbedingungen</li> <li>Hessematrix</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Banachscher_Fixpunktsatz">Banachscher Fixpunktsatz</a></li> <li>Differentialgleichungen <ul> <li>Systeme linearer Differentialgleichungen</li> <li>Anfangswertprobleme</li> <li><a href="http://de.wikipedia.org/wiki/Fundamentalsystem_(Mathematik)">Fundamentalsystem</a></li> <li>Variation der Konstanten</li> <li><a href="http://de.wikipedia.org/wiki/Satz_von_Picard-Lindel%C3%B6f">Satz von Picard-Lindel&ouml;f</a></li> </ul> </li> </ul> <h4>Aufgabenstellungen</h4> <ul> <li>Sind gegebene Mengen offen, abgeschlossen bzw. vollst&auml;ndig?</li> <li>Rand einer Menge besttimmen</li> <li>Lokale und globale Extrema einer Funktion `$f$` bestimmen. Ansatz:<br /> Gradient `$\nabla f$` bestimmen und gleich null setzen. Die Funktionswerte, die das erf&uuml;llen, sind die kritischen Punkte. In Hessematrix einsetzen und Definitheit pr&uuml;fen.</li> <li>L&ouml;sung von nichtlinearen Gleichungssystem</li> <li>Differenzierbarkeit zeigen &rarr; `$\displaystyle \lim_{h \rightarrow 0} \frac{f(x_0+h)-f(x_0)- A \cdot h}{\|h\|}$`</li> <li>L&ouml;sung eines Anfangswertproblems bestimmen</li> <li>&bdquo;Beweisen Sie Existenz und Eindeutigkeit einer L&ouml;sung&ldquo; &rarr; Picard-Lindel&ouml;f</li> <li>Zeigen Sie die rektifizierbarkeit eines Weges `$\gamma$`:<br /> &rarr; Differenzierbarkeit zeigen, ableiten, stetigkeit der Ableitung zeigen.</li> </ul> <h2>Lernplan</h2> <p>Man sollte die Übungsblätter nochmals machen, die relevanten Kapitel im <a href="http://mitschriebwiki.nomeata.de/Ana1.pdf">Skript für Analysis I</a> und im Skript für <a href="http://mitschriebwiki.nomeata.de/SS10/Ana2Bachelor.pdf">Analysis II (Bachelor)</a> durchlesen und Klausuren rechnen. (Aktuellere Skripte finden sich in meinem <a href="https://github.com/MartinThoma/LaTeX-examples/tree/master/documents">GitHub Repository</a>. Allerdings muss man die PDF selbst erstellen.)</p> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Dienstag, den 25. September 2012 von 08:00 bis 13:00 Uhr <strong>Ort</strong>: <a href="http://www.math.kit.edu/iana3/~schmoeger/seite/einteilung/de">Hörsaaleinteilung</a> - Ich bin im <a href="https://maps.google.com/maps?q=49.009522,8.412978&amp;ll=49.009522,8.412979&amp;spn=0.000932,0.002642&amp;num=1&amp;t=m&amp;z=19">Hetz-Hörsaal</a>. <strong>Dauer</strong>: 2 h Analysis I, 1 h Pause, 2 h Analysis II <strong>Punkte</strong>: 7 Aufgaben à 3 Punkte für Analysis I, 7 Aufgaben à 3 Punkte für Analysis II <strong>Bestehensgrenze</strong>: Wohl bei ca. 21 Punkten <strong>Übungsschein</strong>: Ist im Studierendenportal eingetragen <strong>Bonuspunkte</strong>: Gibt es nicht.</p> <h2>Ergebnisse</h2> <p>Die Klausureinsicht ist am 24.10.2012 von 14:00 - 16:30 Uhr (<a href="http://www.math.kit.edu/iana3/lehre/ana22012s/event/einsicht/">Quelle</a>).</p> Mathe-Aufgabe: Blutspende //martin-thoma.com/mathe-aufgabe-blutspende/ Tue, 14 Aug 2012 17:00:16 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/mathe-aufgabe-blutspende <h2>Aufgabenstellung</h2> <p>Ein Mensch hat ca. 5 Liter Blut. Bei einer Blutspende wird in der Regel etwa ein halber Liter Blut entnommen. Bis zur nächsten Blutspende ist wird dieses Blut wieder neu gebildet.</p> <p>Wie häufig muss Blut gespendet werden, bis 95% des ursprünglichen Blutes gespendet wurde?</p> <p>Die natürliche Neubildung von Blut auch ohne Blutspende wird vernachlässigt.</p> <h2>Berechnung</h2> <h3>Die ersten Werte</h3> <p><code>$f: \mathbb{N}_0 \rightarrow \mathbb{R}_0^+$</code> sei die Menge des ursprünglichen Blutes in Liter, das nach <code>$x$</code> Spenden gespendet wurde:</p> <p><code>$f(0) = 0$</code></p> <p>Beim ersten mal Blutspenden wird ein halber Liter des ursprünglichen Blutes gespendet:</p> <p><code>$f(1) = 0{,}5 + f(0)$</code></p> <p>Beim zweiten mal Blutspenden werden 0,45 Liter des ursprünglichen Blutes gespendet:</p> <p><code>$f(2) = \frac{5-0{,}5}{5} \cdot 0{,}5 \text{ Liter} + f(1) + f(0) = 0{,}95 \text{ Liter}$</code></p> <p>Beim dritten mal Blutspenden werden 0,405 Liter des ursprünglichen Blutes gespendet:</p> <p><code>$f(3) = \frac{5-0{,}95}{5} \cdot 0{,}5 \text{ Liter} + f(2) + f(1) + f(0) = 1{,}355 \text{ Liter}$</code></p> <h3>Eine rekursive Formel</h3> <p><code>$ \begin{align} f(1) &amp;= 0{,}5 \\ f(x) &amp;= \overbrace{\underbrace{\frac{5-f(x-1)}{5}}_{\text{Anteil}} \cdot 0{,}5}^{\text{neue Blutmenge}} + f(x-1) \\ &amp;= 0{,}5 - \frac{1}{10} \cdot f(x-1) + f(x-1) \\ &amp;= 0{,}5 + \frac{9}{10} \cdot f(x-1) \end{align} $</code></p> <p>Dabei gilt:</p> <ul> <li>0,5 ist die gespendete Blutmenge in Liter einer Spende</li> <li>`$\frac{9}{10} = \frac{\text{gespendete Blutmenge}}{\text{gesamte Blutmenge}}$`</li> </ul> <h3>Aufl&ouml;sen der Rekursion</h3> <p><code>$ \begin{align} f(4) &amp;= 0{,}5 + \frac{9}{10} \cdot (0{,}5 + \frac{9}{10} \cdot (0{,}5 + \frac{9}{10} \cdot 0{,}5))\\ &amp;= 0{,}5 + \frac{9}{10} \cdot 0{,}5 + (\frac{9}{10})^2 \cdot (0{,}5 + \frac{9}{10} \cdot 0{,}5)\\ &amp;= 0{,}5 + \frac{9}{10} \cdot 0{,}5 + (\frac{9}{10})^2 \cdot 0{,}5 + (\frac{9}{10})^3 \cdot 0{,}5\\ &amp;= 0{,}5 \cdot (1 + \frac{9}{10} + (\frac{9}{10})^2 + (\frac{9}{10})^3)\\ f(x)&amp;= \frac{1}{2} \cdot \sum_{i=0}^{x} (\frac{9}{10})^i \end{align} $</code></p> <h3>Aufl&ouml;sen des Summensymbols</h3> <p><code>$ \begin{align} f(x) &amp;= \frac{1}{2} \cdot \sum_{i=0}^{x} (\frac{9}{10})^i\\ &amp;= \frac{1}{2}\cdot (\frac{0{,}9^{x+1} - 1}{0{,}9 - 1})\\ &amp;= \frac{1}{2}\cdot (-10 \cdot 0{,}9^{x+1} + 10)\\ &amp;= -5 \cdot 0{,}9^{x+1} + 5\\ &amp;= 5 \cdot (1 - 0{,}9^{x+1}) \end{align} $</code></p> <h2>L&ouml;sung</h2> <p><code>$ \begin{align} 0{,}95 \cdot 5 &amp;= 5 \cdot (1- 0{,}9^{x+1})\\ 0{,}95 &amp;= 1 - 0{,}9^{x+1}\\ 0{,}9^{x+1} &amp;= 0{,}05\\ \ln(0{,}9) \cdot {x+1} &amp;= \ln(0{,}05) \\ x &amp;= \frac{\ln(0,05)}{\ln(0{,}9)} - 1\\ x &amp;= 27{,}43 \end{align} $</code></p> <h2>Antwort</h2> <p>Nach dem 28. mal Blutspenden wurden 95% des ursprünglichen Blutes gespendet.</p> Project Euler: Problem 26 //martin-thoma.com/project-euler-problem-26/ Mon, 13 Aug 2012 17:00:49 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/project-euler-problem-26 <p>The task in <a href="http://projecteuler.net/problem=26">Problem 26</a> of Project Euler is:</p> <blockquote>Find the value of d &lt; 1000 for which `$\frac{1}{d}$` contains the longest recurring cycle in its decimal fraction part.</blockquote> <h2>How to solve</h2> <p>Think about how you divide with pen and paper. How do you recognize that you have a cycle?</p> <p>You look at the rest. If you’ve seen the rest before, you are just about to get into the cycle.</p> <h2>My solution</h2> <p>This brute force solution finds the solution instantly.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">unittest</span> <span class="k">def</span> <span class="nf">getCycle</span><span class="p">(</span><span class="n">p</span><span class="p">,</span> <span class="n">q</span><span class="p">):</span> <span class="k">assert</span> <span class="n">p</span> <span class="o">&gt;=</span> <span class="mi">0</span> <span class="k">assert</span> <span class="n">q</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="k">while</span> <span class="n">p</span> <span class="o">&gt;=</span> <span class="n">q</span><span class="p">:</span> <span class="n">p</span> <span class="o">-=</span> <span class="n">q</span> <span class="k">if</span> <span class="n">p</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="c"># p/q is an integer</span> <span class="k">return</span> <span class="s">&quot;&quot;</span> <span class="n">digits</span> <span class="o">=</span> <span class="p">{}</span> <span class="c"># map rest to digit number</span> <span class="c"># for 0.1234567, 1 is the digit #0, 2 digit #1, ...</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">cycle</span> <span class="o">=</span> <span class="s">&quot;&quot;</span> <span class="n">rest</span> <span class="o">=</span> <span class="n">p</span> <span class="k">while</span> <span class="bp">True</span><span class="p">:</span> <span class="n">digits</span><span class="p">[</span><span class="n">rest</span><span class="p">]</span> <span class="o">=</span> <span class="n">i</span> <span class="n">rest</span> <span class="o">*=</span> <span class="mi">10</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">rest</span> <span class="o">/</span> <span class="n">q</span> <span class="n">rest</span> <span class="o">-=</span> <span class="n">tmp</span><span class="o">*</span><span class="n">q</span> <span class="n">cycle</span> <span class="o">+=</span> <span class="nb">str</span><span class="p">(</span><span class="n">tmp</span><span class="p">)</span> <span class="k">if</span> <span class="n">rest</span> <span class="ow">in</span> <span class="n">digits</span><span class="p">:</span> <span class="k">return</span> <span class="n">cycle</span><span class="p">[</span><span class="n">digits</span><span class="p">[</span><span class="n">rest</span><span class="p">]:]</span> <span class="n">i</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">def</span> <span class="nf">euler26</span><span class="p">(</span><span class="n">maximum</span><span class="o">=</span><span class="mi">1000</span><span class="p">):</span> <span class="n">maxCycleLength</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">number</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">maximum</span> <span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">tmp</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">getCycle</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">i</span><span class="p">))</span> <span class="k">if</span> <span class="n">tmp</span> <span class="o">&gt;</span> <span class="n">maxCycleLength</span><span class="p">:</span> <span class="n">maxCycleLength</span> <span class="o">=</span> <span class="n">tmp</span> <span class="n">number</span> <span class="o">=</span> <span class="n">i</span> <span class="k">return</span> <span class="p">(</span><span class="n">number</span><span class="p">,</span> <span class="n">maxCycleLength</span><span class="p">)</span> <span class="k">class</span> <span class="nc">TestSequenceFunctions</span><span class="p">(</span><span class="n">unittest</span><span class="o">.</span><span class="n">TestCase</span><span class="p">):</span> <span class="k">def</span> <span class="nf">setUp</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span> <span class="bp">self</span><span class="o">.</span><span class="n">seq</span> <span class="o">=</span> <span class="nb">range</span><span class="p">(</span><span class="mi">10</span><span class="p">)</span> <span class="k">def</span> <span class="nf">test_simpleSequences</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span> <span class="bp">self</span><span class="o">.</span><span class="n">assertEqual</span><span class="p">(</span><span class="n">getCycle</span><span class="p">(</span><span class="mi">4</span><span class="p">,</span><span class="mi">2</span><span class="p">),</span> <span class="s">&quot;&quot;</span><span class="p">)</span> <span class="bp">self</span><span class="o">.</span><span class="n">assertEqual</span><span class="p">(</span><span class="n">getCycle</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">6</span><span class="p">),</span> <span class="s">&quot;6&quot;</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">9</span><span class="p">):</span> <span class="bp">self</span><span class="o">.</span><span class="n">assertEqual</span><span class="p">(</span><span class="n">getCycle</span><span class="p">(</span><span class="n">i</span><span class="p">,</span><span class="mi">9</span><span class="p">),</span> <span class="nb">str</span><span class="p">(</span><span class="n">i</span><span class="p">))</span> <span class="bp">self</span><span class="o">.</span><span class="n">assertEqual</span><span class="p">(</span><span class="n">getCycle</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">7</span><span class="p">),</span> <span class="s">&quot;142857&quot;</span><span class="p">)</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&#39;__main__&#39;</span><span class="p">:</span> <span class="c">#unittest.main()</span> <span class="k">print</span> <span class="n">euler26</span><span class="p">(</span><span class="mi">1000</span><span class="p">)</span></code></pre></div> Ist die Funktion / Relation wohldefiniert? //martin-thoma.com/ist-die-funktion-relation-wohldefiniert/ Sun, 12 Aug 2012 17:00:14 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ist-die-funktion-relation-wohldefiniert <p>Ich verstehe unter einer wohldefinierten Funktion / Relation die Unabhängigkeit von den Repräsentanten. Wikipedia sagt dazu:</p> <blockquote>Man kann in der Mathematik ein Objekt nicht nur durch eine Definitionsgleichung (explizit), sondern auch durch eine charakteristische Eigenschaft (implizit) definieren. W&auml;hrend eine explizite Definition immer zul&auml;ssig ist, ist eine implizite Definition nur unter der Bedingung zul&auml;ssig, dass es tats&auml;chlich genau ein Objekt mit der angegebenen Eigenschaft gibt. Diese Bedingung nennt man die Wohldefiniertheit der impliziten Definition.</blockquote> <p>Quelle: <a href="http://de.wikipedia.org/wiki/Wohldefiniertheit">Wohldefiniertheit</a></p> <h2>Beispiel 1</h2> <p>Sei <code>$f:\mathbb{Q} \rightarrow \mathbb{Q}$</code> eine Abbildung und definiert durch:</p> <p><code>$f(\frac{p}{q}) := \frac{p}{q}$</code></p> <p><strong>Frage</strong>: Ist <code>$f$</code> wohldefiniert? <strong>Antwort</strong>: Ja. Es sei <code>$\frac{p'}{q'}$</code> die vollständig gekürzte Darstellung von <code>$\frac{p}{q}$</code>. Also gilt: <code>$p = p' \cdot \lambda \land q = q' \cdot \lambda$</code> mit <code>$\lambda \in \mathbb{R} \setminus \{0\}$</code>. <code>$\Rightarrow \frac{p}{q} = \frac{p' \cdot \lambda}{q' \cdot \lambda}$</code>. <code>$\Rightarrow f(\frac{p}{q}) = \frac{p' \cdot \lambda}{q' \cdot \lambda} = \frac{p'}{q'}$</code>. <code>$\Rightarrow f(\frac{p}{q})$</code> ist unabhängig vom Repräsentanten. <code>$\Rightarrow f$</code> ist wohldefiniert <code>$\blacksquare$</code></p> <h2>Beispiel 2</h2> <p>Sei <code>$f:\mathbb{Q} \rightarrow \mathbb{Q}$</code> eine Abbildung und definiert durch:</p> <p><code>$f(\frac{p}{q}) := \frac{p+1}{q}$</code></p> <p><strong>Frage</strong>: Ist <code>$f$</code> wohldefiniert? <strong>Antwort</strong>: Nein.</p> <p><code>$f(\frac{0}{1}) = \frac{0+1}{1} = 1 \neq \frac{1}{2} = \frac{0+1}{2} = f(\frac{0}{2}) \blacksquare$</code></p> <h2>Beispiel 3</h2> <p>Sei <code>$f:\mathbb{Q} \rightarrow \mathbb{Q}$</code> eine Abbildung und definiert durch:</p> <p><code>$f(\frac{p}{q}) := \frac{p-q}{p+q}$</code></p> <p><strong>Frage</strong>: Ist <code>$f$</code> wohldefiniert? <strong>Antwort</strong>: Ja.</p> <p>Es sei <code>$\frac{p'}{q'}$</code> die vollständig gekürzte Darstellung von <code>$\frac{p}{q}$</code>. Also gilt: <code>$p = p' \cdot \lambda \land q = q' \cdot \lambda$</code> mit <code>$\lambda \in \mathbb{R} \setminus \{0\}$</code>.</p> <p><code>$\Rightarrow f(\frac{p}{q}) = f(\frac{\lambda \cdot p'}{\lambda \cdot q'}) = \frac{\lambda \cdot p' - \lambda \cdot q'}{\lambda \cdot p' + \lambda \cdot q'} = \frac{\lambda (p' - q')}{\lambda (p' + q')} = \frac{p' - q'}{p' + q'} \blacksquare$</code></p> Sichtweite des Burdsch Chalifa //martin-thoma.com/sichtweite-des-burdsch-chalifa/ Sun, 12 Aug 2012 13:37:17 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sichtweite-des-burdsch-chalifa <h2>Aufgabenstellung</h2> <p>Der Burdsch Chalifa war 2010 das höchste Gebäude der Erde. Bis zur Spitze sind es 830 m.</p> <p>Angenommen, die Erde wäre eine perfekte Kugel mit einem Radius von 6370 km und die Sicht wäre nicht durch Nebel, Wolken oder sonstige Hindernisse eingeschränkt. Aus welcher Entfernung, die man über die Erde direkt zum Burdsch Chalifa zurücklegt, könnte man den Burdsch Chalifa maximal sehen?</p> <h3>Situationsskizze</h3> <p><a href="../images/2012/08/earth-skizze.png"><img src="../images/2012/08/earth-skizze.png" alt="" title="Situationsskizze f&uuml;r die Berechnung" width="500" height="553" class="aligncenter size-full wp-image-39311" /></a> Gesucht ist die Länge des neongrün hervorgehobenen Kreisbogens x.</p> <h3>Rechenweg</h3> <p><code>$\begin{align} x &amp;= \text{Umfang} \cdot \frac{\varphi}{360^\circ} \\ &amp;= 2 \cdot r \cdot \pi \cdot \frac{\cos^{-1}(\frac{r}{r+h})}{360^\circ} \\ &amp;= 2 \cdot 6370 \text{km} \cdot \pi \cdot \frac{\cos^{-1}(\frac{6370}{6370,83})}{360^\circ} \\ &amp;= 102,8 \text{km} \end{align}$</code></p> <h3>Antwort</h3> <p>Bei optimalen, also unrealistischen, Bedingungen könnte man die Spitze des Burdsch Chalifa noch in 102,8 km entfernung sehen. Dies entspricht übrigens auch dem Punkt auf der Erdoberfläche, der vom Burdsch Chalifa am weitesten entfernt und zu sehen ist. Auch wenn nur die Luftlinie gemessen wird, sind es 102,8 km, da der Erdradius bedeutend größer als der Burdsch Chalifa ist.</p> <p>Laut <a href="http://www.bild.de/lifestyle/bams/burj-chalifa/burj-chalifa-bei-dieser-story-wurde-uns-schwindelig-828-meter-11056462.bild.html">Bildzeitung</a> kann man die Spitze des Burdsch Chalifa noch in 95 km sehen.</p> <h2>Erweiterung der Aufgabenstellung</h2> <p>Das Dorf Mileiha liegt direkt östlich vom Burdsch Chalifa (25° 11’ 50’’ N, 55° 16’ 27’’ O).</p> <p>Wie weit östlich darf das Dorf maximal liegen, damit man die Spitze des Burdsch Chalifa bei optimalen Bedingungen noch sehen kann?</p> <p>Hinweis: Es gelten noch immer die gleichen Voraussetzungen wie im ersten Teil der Aufgabe.</p> <h3>Situationsskizze</h3> <p><a href="../images/2012/08/earth-skizze-21.png"><img src="../images/2012/08/earth-skizze-21.png" alt="" title="Skizze der Erde" width="500" height="299" class="aligncenter size-full wp-image-39411" /></a></p> <p>Gesucht ist die grün eingezeichnete Kurve, die sich über die Erdoberfläche krümmt. Ihre Länge sei x. Um diese zu berechnen, müssen wir wissen welchen Radius die Kreisfläche hat, die entsteht, wenn man die Erde am 25. Breitengrad schneidet. Der Radius dieser Kreisfläche sei <code>$r_{25}$</code>.</p> <h3>Berechnung</h3> <p><code>$ \begin{align} \text{Breitengrad} &amp;= 25 + \frac{11}{60} + \frac{50}{60 \cdot 60} \\ \text{Breitengrad} &amp;= \frac{9071}{360} \approx 25,1972 \\ \cos(\frac{9071}{360}) &amp;= \frac{r_{25,1972}}{6370\text{km}} \\ r_{25,1972} &amp;= \cos(\frac{9071}{360}) \cdot 6370\text{km} \\ r_{25,1972} &amp;\approx 5764\text{km} \end{align} $</code></p> <p>Der soeben errechnete Radius kann einfach in die im ersten Abschnitt erarbeitete Formel eingesetzt werden: <code>$ \begin{align} x &amp;= 2 \cdot r \cdot \pi \cdot \frac{\cos^{-1}(\frac{r}{r+h})}{360^\circ} \\ &amp;= 2 \cdot 5764 \text{km} \cdot \pi \cdot \frac{\cos^{-1}(\frac{5764}{5764,83})}{360^\circ} \\ &amp;\approx 97,8 \text{km} \end{align} $</code></p> <p>Nun sollte man noch berücksichtigen, dass die Beobachter wohl nicht auf der Erde kriechen, sondern ihre Augen in einer Höhe von ca. 1,6m sind:</p> <p><code>$ \begin{align} x &amp;= 2 \cdot 5764 \text{km} \cdot \frac{\pi}{360^\circ} \cdot ( \cos^{-1}(\frac{5764}{5764,83}) + \cos^{-1}(\frac{5764}{5764,0016}) \\ &amp;\approx 102 \text{km} \end{align} $</code></p> <h3>Antwort</h3> <p>Der am weitesten entfernte Punkt, der direkt östlich vom Burdsch Chalifa steht und von dem aus die Spitze des Burdsch Chalifa unter optimalen Bedinungen noch erkannt werden kann, liegt ca. 102 km entfernt.</p> <p>Anmerkung: Mileiha liegt ca. 60 km vom Burdsch Chalifa entfernt. Er müsste also von Mileiha zu sehen sein.</p> Entwurfsmuster-Beispiele //martin-thoma.com/entwurfsmuster-beispiele/ Sat, 11 Aug 2012 17:00:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/entwurfsmuster-beispiele <h2>Singleton</h2> <p><strong>Zweck</strong>: Stelle sicher, dass es nur eine Instanz dieser Klasse gibt. <strong>Beispiel</strong>: <a href="http://docs.oracle.com/javase/6/docs/api/java/lang/Runtime.html#getRuntime%28%29">java.lang.Runtime.getRuntime()</a></p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">Singleton</span> { <span style="color:#777">// an instance of a singleton</span> <span style="color:#088;font-weight:bold">private</span> <span style="color:#088;font-weight:bold">static</span> Singleton instance = <span style="color:#069">null</span>; <span style="color:#777">// private default constructor to prevent the external creation</span> <span style="color:#777">// of more instances</span> <span style="color:#088;font-weight:bold">private</span> Singleton() { } <span style="color:#777">// static method which returns the instance</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#088;font-weight:bold">static</span> <span style="color:#088;font-weight:bold">synchronized</span> Singleton getInstance() { <span style="color:#080;font-weight:bold">if</span> (instance == <span style="color:#069">null</span>) { instance = <span style="color:#080;font-weight:bold">new</span> Singleton(); } <span style="color:#080;font-weight:bold">return</span> instance; } } </pre></div> </div> </div> <h2>Bequemlichkeitsklasse</h2> <p><strong>Zweck</strong>: Faulheit - mache Methodenaufrufe durch änderbare default-Parameter einfacher. Das Bequemlichkeitsmuster ist einfach das Überladen einer Methode:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">Bequemlichkeitsklasse</span> { <span style="color:#777">// convenience class</span> <span style="color:#339;font-weight:bold">int</span> v1, v2, v3; <span style="color:#339;font-weight:bold">int</span> anfrage(<span style="color:#339;font-weight:bold">int</span> p1, <span style="color:#339;font-weight:bold">int</span> p2, <span style="color:#339;font-weight:bold">int</span> p3) { <span style="color:#080;font-weight:bold">return</span> p1 * p2 * p3; } <span style="color:#339;font-weight:bold">int</span> anfrage(<span style="color:#339;font-weight:bold">int</span> p1) { <span style="color:#080;font-weight:bold">return</span> anfrage(p1, v2, v3); } <span style="color:#339;font-weight:bold">int</span> anfrage() { <span style="color:#080;font-weight:bold">return</span> anfrage(v1, v2, v3); } <span style="color:#339;font-weight:bold">void</span> setzeZustand(<span style="color:#339;font-weight:bold">int</span> p1, <span style="color:#339;font-weight:bold">int</span> p2, <span style="color:#339;font-weight:bold">int</span> p3) { v1 = p1; v2 = p2; v3 = p3; } } </pre></div> </div> </div> <h2>Schablonenmethode</h2> <p>Siehe <a href="../java-puzzle-9-template-method-pattern/">Java Puzzle #9: Template method pattern</a>.</p> <h2>Siehe auch</h2> <ul> <li><a href="http://stackoverflow.com/a/2707195/562769">Examples of GoF Design Patterns in Java</a></li> </ul> Java Puzzle #9: Template method pattern //martin-thoma.com/java-puzzle-9-template-method-pattern/ Fri, 10 Aug 2012 17:00:33 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-9-template-method-pattern <p>The following Java Puzzle is an example for the <a href="http://en.wikipedia.org/wiki/Template_method_pattern">template method pattern</a>. It is a design pattern by the <a href="http://en.wikipedia.org/wiki/Design_Patterns">Gang of Four</a>.</p> <p>What is the output of the following snippet: <strong>AbstractClass.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">AbstractClass</span> <span class="o">{</span> <span class="kt">int</span> <span class="nf">templateMethod</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="nf">simpleOperation1</span><span class="o">()</span> <span class="o">*</span> <span class="n">simpleOperation2</span><span class="o">();</span> <span class="o">}</span> <span class="kt">int</span> <span class="nf">simpleOperation1</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">2</span><span class="o">;</span> <span class="o">}</span> <span class="kt">int</span> <span class="nf">simpleOperation2</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">3</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>ConcreteClass.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">ConcreteClass</span> <span class="kd">extends</span> <span class="n">AbstractClass</span> <span class="o">{</span> <span class="nd">@Override</span> <span class="kt">int</span> <span class="nf">simpleOperation1</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">5</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kt">int</span> <span class="nf">simpleOperation2</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="mi">7</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>test.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">ConcreteClass</span> <span class="n">t</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">ConcreteClass</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">t</span><span class="o">.</span><span class="na">templateMethod</span><span class="o">());</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">35</code></pre></div> <p>35</p> <h2>Explanation</h2> <p>You can think of it like this: First, you create the empty class <code>ConcreteClass</code>. It has only the methods inherited by <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Object.html">Object</a> like the <code>constructor</code>, <code>equals()</code> and <code>toString()</code>. Then it gets extended by AbstractClass with <code>templateMethod()</code>, <code>simpleOperation1()</code> and <code>simpleOperation2()</code>. After that, the method overrides <code>simpleOperation1()</code> and <code>simpleOperation2()</code>, but <code>templateMethod()</code> uses them. It uses the methods that are now in <code>ConcreteClass</code>.</p> <p>I don’t know what Java exactly does internally, but thats a good way to think about it. If somebody has more information, please share it as a comment!</p> Java Puzzle #8: Interfaces and Visibility //martin-thoma.com/java-puzzle-8-interfaces-and-visibility/ Thu, 09 Aug 2012 17:00:42 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-8-interfaces-and-visibility <p>What is the output of the following snippets:</p> <p><strong>Shape.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">interface</span> <span class="nc">Shape</span> <span class="o">{</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">draw</span><span class="o">();</span> <span class="kd">private</span> <span class="kt">void</span> <span class="nf">calculateArea</span><span class="o">();</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">printArea</span><span class="o">();</span> <span class="o">}</span></code></pre></div> <p><strong>Rectangle.java</strong></p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">Rectangle</span> <span class="kd">implements</span> <span class="n">Shape</span> <span class="o">{</span> <span class="kd">private</span> <span class="kd">final</span> <span class="kt">int</span> <span class="n">x1</span><span class="o">,</span> <span class="n">x2</span><span class="o">,</span> <span class="n">y1</span><span class="o">,</span> <span class="n">y2</span><span class="o">;</span> <span class="kd">private</span> <span class="kt">int</span> <span class="n">area</span><span class="o">;</span> <span class="kd">public</span> <span class="nf">Rectangle</span><span class="o">(</span><span class="kt">int</span> <span class="n">x1</span><span class="o">,</span> <span class="kt">int</span> <span class="n">y1</span><span class="o">,</span> <span class="kt">int</span> <span class="n">x2</span><span class="o">,</span> <span class="kt">int</span> <span class="n">y2</span><span class="o">)</span> <span class="o">{</span> <span class="k">this</span><span class="o">.</span><span class="na">x1</span> <span class="o">=</span> <span class="n">x1</span><span class="o">;</span> <span class="k">this</span><span class="o">.</span><span class="na">x2</span> <span class="o">=</span> <span class="n">x2</span><span class="o">;</span> <span class="k">this</span><span class="o">.</span><span class="na">y1</span> <span class="o">=</span> <span class="n">y1</span><span class="o">;</span> <span class="k">this</span><span class="o">.</span><span class="na">y2</span> <span class="o">=</span> <span class="n">y2</span><span class="o">;</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">calculateArea</span><span class="o">()</span> <span class="o">{</span> <span class="n">area</span> <span class="o">=</span> <span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">((</span><span class="n">x1</span> <span class="o">-</span> <span class="n">x2</span><span class="o">)</span> <span class="o">*</span> <span class="o">(</span><span class="n">y1</span> <span class="o">-</span> <span class="n">y2</span><span class="o">));</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">draw</span><span class="o">()</span> <span class="o">{</span> <span class="c1">// TODO Auto-generated method stub</span> <span class="o">}</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">printArea</span><span class="o">()</span> <span class="o">{</span> <span class="n">calculateArea</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;My area is &quot;</span> <span class="o">+</span> <span class="n">area</span> <span class="o">+</span> <span class="s">&quot;.&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>test.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">Shape</span> <span class="n">s</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Rectangle</span><span class="o">(</span><span class="mi">0</span><span class="o">,</span> <span class="mi">0</span><span class="o">,</span> <span class="mi">1</span><span class="o">,</span> <span class="mi">1</span><span class="o">);</span> <span class="n">s</span><span class="o">.</span><span class="na">printArea</span><span class="o">();</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">My area is 1.</code></pre></div> <h2>Explanation</h2> <p>Interfaces may not implement anything. So it makes no sense to define private methods. Nevertheless it seems to be valid Java code.</p> Short Educational Clips //martin-thoma.com/short-educational-clips/ Wed, 08 Aug 2012 17:00:37 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/short-educational-clips <p>Here are some clips which are interesting for education. For example, one of then explains the history of the English language in about 10 minutes.</p> <h2>60-Second Adventures in Thought</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/5zVaFjSxAZs" frameborder="0" allowfullscreen=""></iframe> <h2>United Kingdom, Great Britain and England</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/rNu8XDBSn10" frameborder="0" allowfullscreen=""></iframe> <h2>History of English</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/H3r9bOkYW9s" frameborder="0" allowfullscreen=""></iframe> <h2>Electric Vocabulary</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/MBRTR2dlwvA" frameborder="0" allowfullscreen=""></iframe> <h2>DNA Song</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/FUA6_Ucw3i4" frameborder="0" allowfullscreen=""></iframe> <h2>Wakko's 50 State Capitols</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/MSvJ9SN8THE" frameborder="0" allowfullscreen=""></iframe> <h2>Yakko's World</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/x88Z5txBc7w" frameborder="0" allowfullscreen=""></iframe> <h2>The Monty Hall Problem</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/mhlc7peGlGg" frameborder="0" allowfullscreen=""></iframe> <h2>See also</h2> <ul> <li><a href="http://www.youtube.com/user/TEDEducation/videos">TEDEducation</a></li> </ul> Endliche Gruppen //martin-thoma.com/endliche-gruppen/ Wed, 08 Aug 2012 12:03:42 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/endliche-gruppen <p>Endliche Gruppen haben ein paar interessante Eigenschaften. Unter anderem gibt es nur zwei Gruppen mit vier Elementen. alle anderen Gruppen sind isomorph zu diesen Gruppen. Das zeige ich im folgendem.</p> <h2>Gruppen mit vier Elementen</h2> <p>Es gibt genau zwei Gruppen mit vier Elementen. Das sind: <code>$G_1 = (\mathbb{Z}/4\mathbb{Z}, +)$</code> und <code>$G_2 = (\mathbb{Z}/2\mathbb{Z} \times \mathbb{Z}/2\mathbb{Z}, +)$</code></p> <h3>Beweis Teil 1: G<sub>1</sub> und G<sub>2</sub> sind Gruppen</h3> <p>Eine Gruppe <code>$(A, \circ)$</code> müssen drei Eigenschaften erfüllen:</p> <ul> <li>(G1) <strong>Assoziativit&auml;t</strong>: `$\forall a,b,c \in A: (a \circ b) \circ c = a \circ (b \circ c)$`</li> <li>(G2) <strong>Neutrales Element</strong>: `$\exists e \in A \forall a \in A: e \circ a = a \circ e = a$`</li> <li>(G3) <strong>Inverses Element</strong>: `$\forall a \in A \exists a^{-1} \in A: a \circ a^{-1} = a^{-1} \circ a = e$`</li> </ul> <p>Die Verknüpfungstafel für <code>$G_1$</code> lautet:</p> <table class="wikitable" style="width:300px"> <tr> <th>+</th> <th>0</th> <th>1</th> <th>2</th> <th>3</th> </tr> <tr> <th>0</th> <td class="hintergrundfarbe9">0</td> <td>1</td> <td>2</td> <td>3</td> </tr> <tr> <th>1</th> <td>1</td> <td>2</td> <td>3</td> <td class="hintergrundfarbe9">0</td> </tr> <tr> <th>2</th> <td>2</td> <td>3</td> <td class="hintergrundfarbe9">0</td> <td>1</td> </tr> <tr> <th>3</th> <td>3</td> <td class="hintergrundfarbe9">0</td> <td>1</td> <td>2</td> </tr> </table> <p>Man sieht direkt an der Tabelle, dass <strong>0</strong> das neutrale Element ist und jedes Element ein Inverses hat. Für die Assoziativität fällt mir nichts besseres ein, als die 64 Möglichkeiten alle auszuprobieren. Geht das kürzer?</p> <p>Die Verknüpfungstafel für <code>$G_2$</code> lautet:</p> <table class="wikitable" style="width:300px"> <tr> <th>+</th> <th>(0,0)</th> <th>(0,1)</th> <th>(1,0)</th> <th>(1,1)</th> </tr> <tr> <th>(0,0)</th> <td class="hintergrundfarbe9">(0,0)</td> <td>(0,1)</td> <td>(1,0)</td> <td>(1,1)</td> </tr> <tr> <th>(0,1)</th> <td>(0,1)</td> <td class="hintergrundfarbe9">(0,0)</td> <td>(1,1)</td> <td>(1,0)</td> </tr> <tr> <th>(1,0)</th> <td>(1,0)</td> <td>(1,1)</td> <td class="hintergrundfarbe9">(0,0)</td> <td>(0,1)</td> </tr> <tr> <th>(1,1)</th> <td>(1,1)</td> <td>(1,0)</td> <td>(0,1)</td> <td class="hintergrundfarbe9">(0,0)</td> </tr> </table> <p>Das neutrale Element ist hier also <strong>(0,0)</strong>.</p> <h3>Beweis Teil 2: Es gibt keine weiteren Gruppen</h3> <p>Hierfür ist es sehr hilfreich zu wissen, dass die Verknüpfungstafel einer Gruppe immer alle Elemente sowohl in jeder Spalte, als auch in jeder Zeile hat. Dann kann man es Sudoku-mäßig beweisen.</p> <p>Folgendes Skelett gilt immer:</p> <table class="wikitable" style="width:250px"> <tr> <th>+</th> <th>e</th> <th>a</th> <th>b</th> <th>c</th> </tr> <tr> <th>e</th> <td>e</td> <td>a</td> <td>b</td> <td>c</td> </tr> <tr> <th>a</th> <td>a</td> <td></td> <td></td> <td></td> </tr> <tr> <th>b</th> <td>b</td> <td></td> <td></td> <td></td> </tr> <tr> <th>c</th> <td>c</td> <td></td> <td></td> <td></td> </tr> </table> <h4>#1: e auf (1,1)</h4> <p>Wir haben nun folgende Tabelle:</p> <table> <tr> <td> <table class="wikitable" style="width:250px"> <tr> <th>+</th> <th>e</th> <th>a</th> <th>b</th> <th>c</th> </tr> <tr> <th>e</th> <td>e</td> <td>a</td> <td>b</td> <td>c</td> </tr> <tr> <th>a</th> <td>a</td> <td class="hintergrundfarbe7">e</td> <td class="hintergrundfarbe8">c</td> <td class="hintergrundfarbe8">b</td> </tr> <tr> <th>b</th> <td>b</td> <td class="hintergrundfarbe8">c</td> <td></td> <td></td> </tr> <tr> <th>c</th> <td>c</td> <td class="hintergrundfarbe8">b</td> <td></td> <td></td> </tr> </table> </td> <td> <ul> <li>`$b + a = c$` (da a und e in dieser Spalte sind und b in der Zeile ist)</li> <li>`$c + a = b$` (nur b fehlt in der Spalte)</li> <li>`$a + b = c$` (da a und e in dieser Zeile und b in der Spalte bereits vorkommt)</li> <li>`$a + c = b$` (nur b fehlt in der Zeile)</li> </ul> </td> </tr> </table> <h4>#1.1: e auf (2,2)</h4> <table> <tr> <td> <table class="wikitable" style="width:250px"> <tr> <th>+</th> <th>e</th> <th>a</th> <th>b</th> <th>c</th> </tr> <tr> <th>e</th> <td>e</td> <td>a</td> <td>b</td> <td>c</td> </tr> <tr> <th>a</th> <td>a</td> <td>e</td> <td>c</td> <td>b</td> </tr> <tr> <th>b</th> <td>b</td> <td>c</td> <td class="hintergrundfarbe7">e</td> <td class="hintergrundfarbe8">a</td> </tr> <tr> <th>c</th> <td>c</td> <td>b</td> <td class="hintergrundfarbe8">a</td> <td class="hintergrundfarbe8">e</td> </tr> </table> </td> <td> <ul> <li>`$c + c = e$` (genau 1 e pro Zeile / Spalte)</li> <li>`$b + c = a$` (nur a fehlt in der Zeile)</li> <li>`$c + b = a$` (nur a fehlt in der Zeile)</li> </ul> </td> </tr> </table> <p>Diese Lösung enstpricht <code>$G_2$</code>.</p> <h4>#1.2: a auf (2, 2)</h4> <table> <tr> <td> <table class="wikitable" style="width:250px"> <tr> <th>+</th> <th>e</th> <th>a</th> <th>b</th> <th>c</th> </tr> <tr> <th>e</th> <td>e</td> <td>a</td> <td>b</td> <td>c</td> </tr> <tr> <th>a</th> <td>a</td> <td>e</td> <td>c</td> <td>b</td> </tr> <tr> <th>b</th> <td>b</td> <td>c</td> <td class="hintergrundfarbe7">a</td> <td class="hintergrundfarbe8">e</td> </tr> <tr> <th>c</th> <td>c</td> <td>b</td> <td class="hintergrundfarbe8">e</td> <td class="hintergrundfarbe8">a</td> </tr> </table> </td> <td> <ul> <li>`$b + c = e$` (genau 1 e pro Zeile / Spalte)</li> <li>`$c + b = e$` (genau 1 e pro Zeile / Spalte)</li> <li>`$c + c = a$` (nur a fehlt in der Zeile)</li> </ul> </td> </tr> </table> <p>Das entspricht <code>$G_1$</code>. Das sieht man, wenn man …</p> <ol> <li>... die Spalte a und b tauscht</li> <li>... die Zeilen a und b tauscht</li> <li>... die Elemente a und b tauscht</li> </ol> <h4>#2: b auf (1, 1)</h4> <table> <tr> <td> <table class="wikitable" style="width:250px"> <tr> <th>+</th> <th>e</th> <th>a</th> <th>b</th> <th>c</th> </tr> <tr> <th>e</th> <td>e</td> <td>a</td> <td>b</td> <td>c</td> </tr> <tr> <th>a</th> <td>a</td> <td class="hintergrundfarbe7">b</td> <td class="hintergrundfarbe8">c</td> <td class="hintergrundfarbe8">e</td> </tr> <tr> <th>b</th> <td>b</td> <td class="hintergrundfarbe8">c</td> <td class="hintergrundfarbe8">e</td> <td class="hintergrundfarbe8">a</td> </tr> <tr> <th>c</th> <td>c</td> <td class="hintergrundfarbe8">e</td> <td class="hintergrundfarbe8">a</td> <td class="hintergrundfarbe8">b</td> </tr> </table> </td> <td> <ul> <li>`$b + a = c$` (da `$c + a \neq c$` und c noch nicht in der Spalte ist, aber dennoch vorkommen muss)</li> <li>`$c+a =e$` (genau 1 e pro Zeile / Spalte)</li> <li>`$c+b = a$` (da c und e in der Zeile bereits vorkommen und b in der Spalte ist)</li> <li>`$c+c = b$` (da der Rest schon in der Zeile ist)</li> <li>`$b+b = e$` (da a und b in der Spalte sind, c in der Zeile)</li> <li>`$b+c = a$` (da der Rest in der Zeile schon vorkommt)</li> <li>`$a+b = c$` ( - " - )</li> <li>`$a+c = e$`</li> </ul> </td> </tr> </table> <p>Das enspricht wieder <code>$G_1$</code>.</p> <h4>#3: c auf (1, 1)</h4> <table> <tr> <td> <table class="wikitable" style="width:250px"> <tr> <th>+</th> <th>e</th> <th>a</th> <th>b</th> <th>c</th> </tr> <tr> <th>e</th> <td>e</td> <td>a</td> <td>b</td> <td>c</td> </tr> <tr> <th>a</th> <td>a</td> <td class="hintergrundfarbe7">c</td> <td class="hintergrundfarbe8">e</td> <td class="hintergrundfarbe8">b</td> </tr> <tr> <th>b</th> <td>b</td> <td class="hintergrundfarbe8">e</td> <td class="hintergrundfarbe8">c</td> <td class="hintergrundfarbe8">a</td> </tr> <tr> <th>c</th> <td>c</td> <td class="hintergrundfarbe8">b</td> <td class="hintergrundfarbe8">a</td> <td class="hintergrundfarbe8">e</td> </tr> </table> </td> <td> <ul> <li>`$a+b = e$` (a, c bereits in Zeile, b in Spalte)</li> <li>`$a+c = b$` (a, c, e in Zeile)</li> <li>`$b+a = e$` (a, c in Spalte, b in Zeile)</li> <li>`$c+c = e$` (letztes e)</li> <li>`$b+c = a$` (b, c, e in Spalte)</li> <li>`$b+b = c$` (b, e, a in Zeile)</li> <li>`$c+a = b$` (a, c, e in Spalte)</li> <li>`$c+b = a$` (b, e, c in Spalte)</li> </ul> </td> </tr> </table> <p>Das entspricht <code>$G_1$</code>. Das sieht man, wenn man …</p> <ol> <li>... die Spalte b und c tauscht</li> <li>... die Zeilen b und c tauscht</li> <li>... die Elemente b und c tauscht</li> </ol> Permutationen und Transpositionen //martin-thoma.com/permutationen-und-transpositionen/ Wed, 08 Aug 2012 10:36:06 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/permutationen-und-transpositionen <h2>Permutation</h2> <h3>Definition</h3> <div class="definition">Es sei M eine endliche Menge. Eine bijektive Selbstabbildung von M heißt <strong>Permutation</strong>. Die Menge \(S_M\) der Permutationen von M ist eine Gruppe bezüglich der Verkettung \(\circ\) von Abbildungen und heißt symmetrische Gruppe von M.</div> <p>Quelle: <a href="https://studium.kit.edu/sites/vab/0x40F0348A9ACDCE49A96EEE39EB076112/Vorlesungsunterlagen/LA.pdf">Skript</a> von Herrn Prof. Dr. Leuzinger, KIT</p> <h3>Allgemeines</h3> <p>Es ist nun egal, ob ich die Permutationen von {1, 2, 3} oder {42, 1337, ABC} anschaue. Es sind einfach nur drei Objekte, die unterscheidbar sind. Um es einfacher zu machen, gehen wir nun von den Objekten {1, 2, …, m} aus. Alle Permutationen dieser Objekte bilden eine Gruppe. Diese nennen wir <span>\(S_m\)</span>.</p> <p>Ein einzelnes Element aus <span>\(S_m\)</span> wird meist <span>\(\pi\)</span> oder <span>\(\sigma\)</span> genannt, also <span>\(\pi \in S_m\)</span>. Da <span>\(\pi\)</span> eine Permutation ist, ist es insbesondere eine bijektive Selbstabbildung, also:</p> <p>\[M = {1, …, m}\] \[\pi: M \rightarrow M\] \[i \mapsto \pi(i)\]</p> <p>Kurz schreibt man auch: <span>\(\pi = \begin{pmatrix} 1 &amp; 2 &amp; 3 &amp; ... &amp; m\\ \pi(1) &amp; \pi(2) &amp; \pi(3) &amp; ... &amp; \pi(m) \end{pmatrix}\)</span></p> <h3>Anzahl der Permutationen</h3> <p>Wenn ich n Elemente habe, die ich auf n Plätze verteilen muss: Wie viele unterschiedliche Zuordnungen von Elementen zu den Plätzen gibt es?</p> <p>Die Antwort ist <span>\(n! = 1 \cdot 2 \cdot ... (n - 1) \cdot n = \prod_{i=1}^n i\)</span>. Für das erste Element sind <span>\(n\)</span> Plätze frei. Das Zweite kann nur noch auf <span>\((n-1)\)</span> Plätze verteilt werden, … , das letzte hat nur noch einen Platz zur “Auswahl”.</p> <h3>Erzeugung der Permutationen</h3> <p>Angenommen, man muss in einem Test <span>\(S_3\)</span> explizit angeben. Wie geht das?</p> <p>Nun, zu erst erzeugt man alle Permutationen. Dafür rechnet man sich die Anzahl aus. Es gibt 3 Elemente, also <span>\(3 \cdot 2 \cdot 1 = 6\)</span> Permutationen: 1. _ _ _ 2. _ _ _ 3. _ _ _ 4. _ _ _ 5. _ _ _ 6. _ _ _</p> <p>Nun zuerst zum ersten Element, der 1. Diese kann ich an die erste, die zweite oder die dritte Stelle verschieben. Also: 1. 1 _ _ 2. 1 _ _ 3. _ 1 _ 4. _ 1 _ 5. _ _ 1 6. _ _ 1</p> <table> <tr> <td>Nun zum zweiten Element, der 2. Wieder das gleiche Prinzip:</td> <td>Und nun nur noch das letzte Einfüllen:</td> </tr> <tr> <td>1. 1 2 _ 2. 1 _ 2 3. 2 1 _ 4. _ 1 2 5. 2 _ 1 6. _ 2 1</td> <td>1. 1 2 3 2. 1 3 2 3. 2 1 3 4. 3 1 2 5. 2 3 1 6. 3 2 1</td> </tr> </table> <p>Und nun noch als Menge in der mathematischen Schreibweise aufschreiben:</p> <p><span>\(S_3 = \left \{ \underbrace{\begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 1 &amp; 2 &amp; 3 \end{pmatrix}}_{\pi_1}, \underbrace{\begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 1 &amp; 3 &amp; 2 \end{pmatrix}}_{\pi_2}, \underbrace{\begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 2 &amp; 1 &amp; 3 \end{pmatrix}}_{\pi_3}, \underbrace{\begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 3 &amp; 1 &amp; 2 \end{pmatrix}}_{\pi_4}, \underbrace{\begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 2 &amp; 3 &amp; 1 \end{pmatrix}}_{\pi_5}, \underbrace{\begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 3 &amp; 2 &amp; 1 \end{pmatrix}}_{\pi_6} \right \}\)</span></p> <h3>Verkettung</h3> <p>Was passiert, wenn ich die Permuation <span>\(\pi_2\)</span> mit der Permutation <span>\(\pi_3\)</span> verkette? Also: <span>\(\pi_x(i) = \pi_2(\pi_3(i)) = \begin{pmatrix}1 &amp; 2 &amp; 3\\ 3 &amp; 1 &amp; 2 \end{pmatrix} = \pi_6\)</span> Aber:</p> <p><span>\(\pi_y(i) = \pi_3(\pi_2(i)) = \begin{pmatrix}1 &amp; 2 &amp; 3\\ 2 &amp; 3 &amp; 1 \end{pmatrix} = \pi_5 \neq \pi_6\)</span></p> <p>Die Verkettung von Permutationen ist also nicht kommutativ!</p> <p>Es ergibt sich insgesamt folgende Verknüfungstabelle (gelesen wird: Zeile zuerst, Spalte später):</p> <table> <tr> <th style="border-right: 1px solid #000;border-bottom: 1px solid #000;">&nbsp;</th> <th style="border-bottom: 1px solid #000;"><span>\(\pi_1\)</span></th> <th style="border-bottom: 1px solid #000;"><span>\(\pi_2\)</span></th> <th style="border-bottom: 1px solid #000;"><span>\(\pi_3\)</span></th> <th style="border-bottom: 1px solid #000;"><span>\(\pi_4\)</span></th> <th style="border-bottom: 1px solid #000;"><span>\(\pi_5\)</span></th> <th style="border-bottom: 1px solid #000;"><span>\(\pi_6\)</span></th> </tr> <tr> <th style="border-right: 1px solid #000;"><span>\(\pi_1\)</span></th> <td><span>\(\pi_1\)</span></td> <td><span>\(\pi_2\)</span></td> <td><span>\(\pi_3\)</span></td> <td><span>\(\pi_4\)</span></td> <td><span>\(\pi_5\)</span></td> <td><span>\(\pi_6\)</span></td> </tr> <tr> <th style="border-right: 1px solid #000;"><span>\(\pi_2\)</span></th> <td><span>\(\pi_2\)</span></td> <td><span>\(\pi_1\)</span></td> <td><span>\(\pi_5\)</span></td> <td><span>\(\pi_6\)</span></td> <td><span>\(\pi_3\)</span></td> <td><span>\(\pi_4\)</span></td> </tr> <tr> <th style="border-right: 1px solid #000;"><span>\(\pi_3\)</span></th> <td><span>\(\pi_3\)</span></td> <td><span>\(\pi_4\)</span></td> <td><span>\(\pi_1\)</span></td> <td><span>\(\pi_2\)</span></td> <td><span>\(\pi_6\)</span></td> <td><span>\(\pi_5\)</span></td> </tr> <tr> <th style="border-right: 1px solid #000;"><span>\(\pi_4\)</span></th> <td><span>\(\pi_4\)</span></td> <td><span>\(\pi_3\)</span></td> <td><span>\(\pi_6\)</span></td> <td><span>\(\pi_5\)</span></td> <td><span>\(\pi_1\)</span></td> <td><span>\(\pi_2\)</span></td> </tr> <tr> <th style="border-right: 1px solid #000;"><span>\(\pi_5\)</span></th> <td><span>\(\pi_5\)</span></td> <td><span>\(\pi_6\)</span></td> <td><span>\(\pi_2\)</span></td> <td><span>\(\pi_1\)</span></td> <td><span>\(\pi_4\)</span></td> <td><span>\(\pi_3\)</span></td> </tr> <tr> <th style="border-right: 1px solid #000;"><span>\(\pi_6\)</span></th> <td><span>\(\pi_6\)</span></td> <td><span>\(\pi_5\)</span></td> <td><span>\(\pi_4\)</span></td> <td><span>\(\pi_3\)</span></td> <td><span>\(\pi_2\)</span></td> <td><span>\(\pi_1\)</span></td> </tr> </table> <p>Man sieht nun, und das finde ich durchaus erstaunlich, man landet immer wieder in <span>\(S_3\)</span>. Durch die Verknüpfung von Permutationen kommt also <em>immer</em> wieder eine Permutation heraus! Das bedeutet, <span>\(\)</span> ist unter dieser Verknüpfung abgeschlossen.</p> <p>Man kann nun auch noch sehen, jedes Element aus <span>\((S_3, \circ)\)</span> ein inverses hat, da in jeder Zeile ein mal <span>\(\pi_1\)</span> vorkommt.</p> <p>Außerdem ist <span>\((S_3, \circ)\)</span> assoziativ.</p> <p>Kurz: <span>\((S_3, \circ)\)</span> ist eine Gruppe, die jedoch nicht abelsch ist.</p> <p>Es wurde in der Vorlesung auch gezeigt, dass allgemein <span>\((S_m, \circ)\)</span> eine Gruppe ist.</p> <h3>Die Fehlstandszahl</h3> <div class="definition">Es sei \(\pi \in S_m\) eine Permutation. Die <strong>Fehlstandszahl</strong> <span>\(F(\pi)\)</span> von <span>\(\pi\)</span> ist die (eindeutige) Anzahl der Fälle, in denen für <span>\(i &lt; k\)</span> gilt <span>\(\pi(i) &gt; \pi(k)\)</span>. Die Permutationen mit gerader Fehlstandszahl <span>\(F(\pi)\)</span> hei&szlig;en gerade, die Permutationen mit ungerader Fehlstandszahl hei&szlig;en ungerade.</div> <h4>Beispiele</h4> <p><span>\(\pi_1 = \begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 1 &amp; 2 &amp; 3 \end{pmatrix}\)</span> hat die Fehlstandszahl 0.</p> <p><span>\(\pi_2 = \begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 1 &amp; 3 &amp; 2 \end{pmatrix}\)</span> hat die Fehlstandszahl 1, da <span>\(i = 2 &lt; 3 = k\)</span> gilt, aber <span>\(\pi_2(2) = 3 &gt; 2 = \pi_2(3)\)</span>.</p> <p><span>\(\pi_3 = \begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 2 &amp; 1 &amp; 3 \end{pmatrix}\)</span> hat die Fehlstandszahl 1.</p> <p><span>\(\pi_4 = \begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 3 &amp; 1 &amp; 2 \end{pmatrix}\)</span> hat die Fehlstandszahl 2.</p> <p><span>\(\pi_5 = \begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 2 &amp; 3 &amp; 1 \end{pmatrix}\)</span> hat die Fehlstandszahl 2.</p> <p><span>\(\pi_6 = \begin{pmatrix} 1 &amp; 2 &amp; 3 \\ 3 &amp; 2 &amp; 1 \end{pmatrix}\)</span> hat die Fehlstandszahl 2.</p> <h2>Transposition</h2> <div class="definition">Eine <strong>Transposition</strong> ist eine Permutation aus \(S_m\), bei der zwei verschiedene, fest gewahlte Zahlen \(i, k \in \{1, 2, ..., m\}\) vertauscht werden, während alle anderen Zahlen fest bleiben. Man schreibt fur diese Transposition auch kurz \((i~k)\).</div> <p>Transpositionen werden gerne mit <span>\(\tau\)</span> abgekürzt.</p> <p>Also: <span>\(\pi_2 = (2~3), \pi_3=(1~2), \pi_6 = (1~3)\)</span> sind Transpositionen. <span>\(\pi_1, \pi_4, \pi_5\)</span> sind keine Transpositionen.</p> <p>Es gilt: <span>\(\tau \circ \tau = id\)</span></p> <p>wir haben in der Vorlesung gezeigt:</p> <div class="satz">Jede Permutation <span>\(\pi \in S_m, m \geq 2,\)</span> lässt sich als Verkettung von Transpositionen darstellen.</div> <p>Beispiel: <span>\(\sigma = \begin{pmatrix}1 &amp; 2 &amp; 3 &amp; 4 &amp; 5 &amp; 6 \\ 6 &amp; 5 &amp; 4 &amp; 1 &amp; 3 &amp; 2\end{pmatrix} = (1~6) \circ (2~5) \circ (3~4) \circ (4~6) \circ (5~6)\)</span></p> <p>Gelesen wird das ganze von rechts nach links. Die Transposition <span>\((5~6)\)</span> wird also zuerst angewendet. Wie bei Abbildungen die verkettet werden halt auch.</p> <p>Die Fehlstandszahl von <span>\(\sigma\)</span> ist 13 und die Anzahl der Transpositionen ist ungerade.</p> <p>Interessanterweise gilt auch <span>\(\sigma = (1~4) \circ (3~5) \circ (2~6) \circ (1~3) \circ (1~2)\)</span>. Außerdem kann man beliebig häufig eine Transposition doppelt hinzufügen, da es ja die Identität ist. Die Darstellung einer Permutation als folge von Transpositionen ist also nicht eindeutig.</p> <h2>Siehe auch</h2> <p>Wikipedia: <a href="http://de.wikipedia.org/wiki/Permutation">Permutation</a></p> Flags of the Earth //martin-thoma.com/flags-of-the-earth/ Tue, 07 Aug 2012 17:00:47 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/flags-of-the-earth <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/07/flags-of-the-earth.png"><img src="../images/2012/07/flags-of-the-earth.png" alt="Flags of the Earth" width="" height="" class="size-full wp-image-37071" /></a><p class="wp-caption-text">Flags of the Earth</p></div> <p><strong>Go to the Game</strong>: <a href="http://www.kongregate.com/games/KingDotCom/flags">Flags on Kongregate</a> <strong>Task</strong>: Say which country the shown flag belongs to. <strong>How to play</strong>: Click on on of the 4 - 5 countries. <strong>My Record</strong>: 40 Flags and 12662 points.</p> Klausur Lineare Algebra I + II //martin-thoma.com/klausur-lineare-algebra-i-ii/ Tue, 07 Aug 2012 09:35:33 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/klausur-lineare-algebra-i-ii <p>Dieser Artikel richtet sich vor allem an Studenten, die im Sommersemester 2012 bei Herrn Prof. Dr. Leuzinger am KIT die Klausur über Lineare Algebra und analytische Geometrie schreiben werden.</p> <p>Was ich im folgenden unter “Themen” schreibe, wurde von Prof. Dr. Leuzinger in der letzten Stunde aufgeschrieben. Das habe ich als Grundlage genommen und ergänzt. Er gab folgende Tipps:</p> <ul> <li>Zeitplan aufstellen</li> <li>Aktiv lernen</li> </ul> <p>Ich kann als Tipp für die Klausur noch sagen: Wenn du eine Aufgabe (b) machst, überleg dir, ob dir die Ergebnisse aus (a) helfen können! In den LA-Klausuren, die ich bisher gesehen habe, hat die vorangehende Teilaufgabe sehr häufig eine Hilfestellung geboten.</p> <h2 id="vorbereitung">Vorbereitung</h2> <h3 id="lineare-algebra-i">Lineare Algebra I</h3> <p>Ihr solltet auf jeden Fall die <a href="../lernkontrolle-lineare-algebra-i/" title="Lernkontrolle: Lineare Algebra I">Lernkontrolle: Lineare Algebra I</a> machen.</p> <h4 id="themen">Themen</h4> <ul> <li><strong>Gruppen</strong>: Untergruppe, Homomorphismus/Isomorphismus, `$GL(n, \mathbb{K})$`</li> <li><strong>K&ouml;rper</strong>: `$\mathbb{R}, \mathbb{C}, \mathbb{Z}/p\mathbb{Z}$` (insbesondere `$p=2$`)</li> <li><strong>Vektorr&auml;ume</strong>: Basis, Basiserg&auml;nzungssatz, Dimension, Basiswechsel, `$V \cong \mathbb{K}^n$` (f&uuml;r `$\dim V = n$`); `$\dim (U_1 \oplus U_2) = \dim U_1 + \dim U_2$`</li> <li><strong>Lineare Abblidungen</strong> (Definitionen, Beispiele): <ul> <li>Lineare Fortsetzung, `$\phi: V \rightarrow W$`</li> <li>Dimensionssatz `$\dim \text{Bild} \phi = \dim V - \dim \phi^2$`</li> <li>`$\text{Hom}(V, W) \cong \mathbb{K}^{m \times n}$` Abbildungsmatrix</li> <li><b>Dualraum</b>: `$W = \mathbb{R}$`, `$V^* = \text{Hom}(V, \mathbb{K})$`</li> <li>`$\phi: V \rightarrow W$` A</li> <li>`$\phi: W* \rightarrow V*$` `$A^T$`</li> <li>duale Basis, duale Abbildung</li> <li>Basiswechsel f&uuml;r Endomorphismen, Formel</li> <li>`$\tilde{A} = S^{-1} A S$`, S = Matrix des Basiswechsels</li> </ul> </li> <li><strong>Determinante</strong>: <ul> <li>Laplacesche Entwicklungsformel (z.B. nach i-ter Spalte)</li> <li>`$\det A^T = \det A$`</li> <li>`$\det(A \cdot B) = \det A \cdot \det B$`</li> <li>`$\det(A^{-1}) = \frac{1}{\det A}$`</li> <li>`$\det \begin{pmatrix}A &amp; * \\0 &amp; B\end{pmatrix} = \det A \cdot det(B)$` ("K&auml;stchensatz")</li> <li>Bei beliebig gro&szlig;en Matrizen &agrave; la `$A \in \mathbb{R}^{n \times n}$` gibt es ein paar Dinge, die beim Suchen der Determinante hilfreich sein k&ouml;nnen: <ul> <li>Ist die Matrix symmetrisch? Falls ja, muss man sich nur die Zeilen anschauen. Falls nein, k&ouml;nnen die folgenden Tipps sowohl f&uuml;r die Zeilen als auch f&uuml;r die Spalten &uuml;berpr&uuml;ft werden.</li> <li>N&uuml;tzt es etwas, wenn ich auf die letzte Zeile alle vorherigen Zeilen addiere?</li> <li>Was passiert, wenn ich Zeile `$i$` auf Zeile `$(i+1)$` addiere f&uuml;r `$i \in 1, ..., (n-1)$`?</li> </ul> </li> </ul> </li> <li><a href="../wie-bestimme-ich-das-inverse-einer-matrix/">Wie bestimme ich das Inverse einer Matrix?</a></li> <li><strong>L&ouml;sungstheorie von LGSen</strong> (Gau&szlig;-Algorithmus)</li> <li><strong>Eigenwerte</strong>, Eigenvektoren (`$\phi(x) = \lambda x, x \neq 0$`)</li> <li>charakteristisches Polynom `$\phi|_{[x]} = \lambda_{id_{[x]}}$` - <a href="../wie-berechnet-man-das-charakteristische-polynom/">Wie berechnet man das charakteristische Polynom?</a></li> <li>`$\mathbb{K} = \mathbb{C} \leadsto$` <strong>Jordansche Normalform</strong> (Algorithmus)</li> </ul> <h4>Aufgabenstellungen</h4> <p>Mit diesen Aufgabentypen sollte man rechnen:</p> <ul> <li>Gegeben sind zwei Untervektorr&auml;ume `$U, V$` des `$\mathbb{R}^4$`. Finden Sie jeweils eine Basis von `$U, V, U \cap V, U + V$`. &rarr; <a href="../wie-bildet-man-den-schnitt-zweier-vektorraume/">Erkl&auml;rung</a></li> <li>Bestimmen Sie alle L&ouml;sungen eines Gleichungssystems (auch in endlichen K&ouml;rpern wie `$\mathbb{Z} / 5 \mathbb{Z}$`!).</li> <li>Bestimmen Sie die Jordansche Normalform einter Matrix A. &rarr; <a href="../wie-berechnet-man-die-jordansche-normalform/">Erkl&auml;rung</a></li> </ul> <h4>Good to know</h4> <p>Ähnlichkeitsinvariante Matrizeneigenschaften:</p> <ul> <li>Rang</li> <li>Spur</li> <li>Determinante</li> <li>Jordansche Normalform</li> <li>Charakteristisches Polynom</li> </ul> <ul> <li><a href="http://math.stackexchange.com/a/14079/6876">Wie findet man heraus, ob zwei Matrizen &auml;hnlich sind?</a></li> <li><a href="http://de.wikipedia.org/wiki/Regul%C3%A4re_Matrix#Invertierbare_Matrizen_.C3.BCber_einem_K.C3.B6rper">Wann sind Matrizen regul&auml;r?</a></li> </ul> <h4>Siehe auch</h4> <ul> <li><a href="http://commons.wikimedia.org/wiki/File:Venn-diagramm-algebraische-strukturen.svg">&Uuml;bersicht &uuml;ber algebraische Strukturen</a></li> <li><a href="http://next-internet.com/la/texte/la_zusammenfassung.pdf">Zusammenfassung auf next-indernet.com</a></li> </ul> <h3>Lineare Algebra II</h3> <h4>Themen</h4> <ul> <li><strong>Vektorr&auml;ume mit Skalarprodukt</strong> (Definition, Beispiele, `$\mathbb{K} \in \{\mathbb{R}, \mathbb{C}\}$`)</li> <li>`$G = G^T$` (`$\mathbb{K} = \mathbb{R}$`)</li> <li>`$G = \bar{G}^T$` (`$\mathbb{K} = \mathbb{C}$`)</li> <li>Basiswechsel `$\tilde{G} = S^T G S$` (allgemeiner Basiswechsel)</li> <li>Basiswechsel `$\tilde{G} = S^{-1} G S$` (f&uuml;r ONB, da `$S^{-1} = S^T$`)</li> <li>Skalarprodukt induziert eine Norm, `$\| x \| = \sqrt{\langle x, x \rangle}$`</li> <li>Parallelogramm-Identit&auml;t: `$\|a+b\|^2 + \|a-b\|^2 = 2 \cdot (\|a\|^2 + \|b\|^2)$`</li> <li>`$\cos \omega(a,b) = \frac{\langle a, b \rangle}{\|a\| \cdot \| b \|}$`</li> <li>Orthogonal, ONB, Orthogonal-Komplement</li> <li>`$x \perp y$`, `$\langle x, y \rangle = 0$`</li> <li>orthogonale / unit&auml;re Matrizen: <ul> <li>`$S \cdot S^T = E$`</li> <li>`$\det S \cdot \det S^T = \det E = 1$`</li> <li>`$U \cdot \bar U^T = E$`</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Gram-Schmidtsches_Orthogonalisierungsverfahren">Gram-Schmidtsches Orthogonalisierungsverfahren</a>: `$w_j = v_j - \sum_{i=1}^{j-1} \frac{\langle v_j, w_i \rangle}{\langle w_i, w_i \rangle} \cdot w_i$`</li> <li>Projektion eines Vektors auf eine Ebene (&Uuml;B 4, A3)</li> <li>"Gute" Abbildungen bzgl. `$\langle, \rangle: \phi: V \rightarrow V$`</li> <li>(Selbst-)adjungierte: `$\langle \phi(x), y \rangle = \langle x, \phi*(y) \rangle \rightarrow A = A^T$`</li> <li>Lineare Isometrien `$\langle \phi(x), \phi(y) \rangle \rightarrow A$` orthogonal<br />`$\varphi$` hei&szlig;t lineare Isometrie `$:\Leftrightarrow \langle \varphi(x), \varphi(y) \rangle = \langle x, y \rangle$`</li> <li>Abbildungsmatrizen bzgl. ONB</li> <li>Spektralsatz: `$\phi s.a. \Rightarrow \phi \text{ diagonalisierbar}, \exists S \in O(n) \text{ mit } S^{-1} A S = D$`.</li> <li>Abbildungsmatrizen bzgl. ONB</li> <li>`$\phi$` s.a. Basis: ONB `$\Rightarrow$` Abb. Matrix symmetrisch, aber noch mehr: `$\exists$` ONB aus EV mit Abb. Matrix = Diagonalmatrix (Spektralsatz)</li> <li>`$\phi$` lin. Isometrie, Basis ONB `$\Rightarrow$` Abb. Matrix ist orthogonal / unit&auml;r, aber noch mehr: `$\exists$` ONB mit Abb. in euklid NF</li> <li><strong><a href="../berechnung-der-euklidischen-normalform/">Berechnung der euklidischen Normalform</a></strong></li> <li>Kiterien f&uuml;r pos. definit (Ist geg. BF `$\beta$` ein SP?)</li> <li><a href="http://de.wikipedia.org/wiki/Hauptachsentransformation">Hauptachsentransformation</a></li> <li>`$(V, \langle , \rangle)$` VR mit SP. `$\beta = $` Bilinearform kann man simultan diagonalisieren `$\exists$` ONB von `$V$`, so dass Matrix von `$\langle, \rangle E_n$` (nach Definition von ONB)</li> <li><a href="http://de.wikipedia.org/wiki/Hurwitzpolynom#Hurwitz-Kriterium">Hurwitz-Kriterium</a></li> </ul> <p>Affine / Euklidische Geometrie <code>$\operatorname{Aff}(\mathbb{R}^n), \mathrm{Iso}(\mathbb{R}^n)$</code> Gruppe der Affinität bzgl. Isometrie</p> <h2>Lernplan</h2> <p>Es empfiehlt sich, einen Lernplan aufzustellen. Wenn ich die Übungsblätter mache, dann lese ich mir zuerst die relevanten Kapitel im <a href="https://studium.kit.edu/sites/vab/0x40F0348A9ACDCE49A96EEE39EB076112/Vorlesungsunterlagen/Forms/AllItems.aspx">Skript</a> durch.</p> <h2>Termine und Klausurablauf</h2> <p><strong>Datum</strong>: Donnerstag, den 13. September 2012 von 08:00 bis 13:00 Uhr<br /> <strong>Ort</strong>: bei mir: <strike>Neue Chemie</strike> Hörsaal am Fasanengarten (→ <a href="http://www.math.kit.edu/iag2/lehre/la2mathe20122012s/media/hoersaele-1.pdf">Hörsaaleinteilung</a>)<br /> <strong>Dauer</strong>: 2 h LA I, 1 h Pause, 2 h LA II<br /> <strong>Punkte</strong>: 6 Aufgaben à 4 Punkte für LA I, 6 Aufgaben à 4 Punkte für LA II<br /> <strong>Geschwindigkeit</strong>: <code>$\frac{5 \text{ Minuten}}{\text{Punkt}}$</code><br /> <strong>Übungsschein</strong>: Noch nicht im Studierendenportal (Stand: 11.09.2012)<br /> <strong>Bonuspunkte</strong>: Gibt es nicht.<br /></p> <p><strong>Nicht vergessen</strong>:</p> <ul> <li>Studentenausweis</li> <li>Leere Bl&auml;tter</li> <li>Essen und Trinken (4h Klausur!!!)</li> </ul> <p>Ein paar interessante Aussagen:</p> <blockquote>In den letzten Jahren reichten 20 Punkte zum bestehen</blockquote> <blockquote>In den letzten Jahren wurde jeweils im LA I und in LA II der beste Teil doppelt bepunktet</blockquote> <blockquote>Es gab bisher nur eine Gesamtnote f&uuml;r LA I und II, man musste die beiden Tests also nicht einzeln bestehen.</blockquote> <h2 id="ergebnisse">Ergebnisse</h2> <p>Ich habe den Übungsleiter mal angeschrieben. Das war seine Antwort:</p> <blockquote> Der Termin ist normalerweise in der ersten Vorlesungswoche. Er wird auf der Kurshomepage rechtzeitig bekannt gegeben. </blockquote> <blockquote>Die Ergebnisse der Klausur werden am Freitag, den 05.10.2012, im Allianzgeb&auml;ude am schwarzen Brett neben 4A-09 ausgeh&auml;ngt.</blockquote> <p>Das ist vermutlich im Allianzbau.</p> <p>Die Klausureinsicht findet am Montag, den 15.10.2012 von 15:00 - 16:30 Uhr im Raum 1C-03 im Allianzgebäude statt.</p> Globetrotter //martin-thoma.com/globetrotter/ Mon, 06 Aug 2012 17:00:06 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/globetrotter <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/07/globetrotter-xl.png"><img src="../images/2012/07/globetrotter-xl.png" alt="Globetrotter - A game to learn cities and countries" width="" height="" class="size-full wp-image-37021" /></a><p class="wp-caption-text">Globetrotter - A game to learn cities and countries</p></div> <p><strong>Go to the Game</strong>: <a href="http://www.kongregate.com/games/crafics/globetrotter-xl">Globetrotter XL</a> on Kongregate <strong>Task</strong>: Find a city on a map <strong>How to play</strong>: You’re given the name of a city and its country and a map. In the first levels this map has borders, but no names of countries or cities. In the later levels even the borders are not shown. <strong>My Record</strong>: Level 6, about 1400 points</p> Java Puzzle #7: Inheritance and Visibility //martin-thoma.com/java-puzzle-7-inheritance-and-visibility/ Sun, 05 Aug 2012 17:00:38 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-7-inheritance-and-visibility <p>You are given the following two classes: <strong>Animal.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">Animal</span> <span class="o">{</span> <span class="kd">private</span> <span class="kd">final</span> <span class="kt">int</span> <span class="n">height</span> <span class="o">=</span> <span class="mi">120</span><span class="o">;</span> <span class="o">}</span></code></pre></div> <p><strong>Tiger.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">Tiger</span> <span class="kd">extends</span> <span class="n">Animal</span> <span class="o">{</span> <span class="kd">public</span> <span class="kt">int</span> <span class="n">height</span><span class="o">;</span> <span class="o">}</span></code></pre></div> <p>What is the output of the following three snippets: <strong>test1.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test1</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">Tiger</span> <span class="n">t</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Tiger</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">t</span><span class="o">.</span><span class="na">height</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>test2.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test2</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">Animal</span> <span class="n">t</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Tiger</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">t</span><span class="o">.</span><span class="na">height</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>test3.java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test3</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">Animal</span> <span class="n">t</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Animal</span><span class="o">();</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">t</span><span class="o">.</span><span class="na">height</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <p><strong>test1.java</strong>:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">0</code></pre></div> <p><strong>test2.java</strong>:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Exception in thread <span class="s2">&quot;main&quot;</span> java.lang.Error: Unresolved compilation problem: The field Animal.height is not visible at test.main<span class="o">(</span>test.java:4<span class="o">)</span></code></pre></div> <p><strong>test3.java</strong>:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Exception in thread <span class="s2">&quot;main&quot;</span> java.lang.Error: Unresolved compilation problem: The field Animal.height is not visible at test.main<span class="o">(</span>test.java:4<span class="o">)</span></code></pre></div> Java Puzzle #6: Double Arithmetic //martin-thoma.com/java-puzzle-6-double-arithmetic/ Sat, 04 Aug 2012 17:00:27 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-6-double-arithmetic <p>What is the output of the following snippet?</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">a</span> <span class="o">=</span> <span class="mf">1.3378901234567877</span><span class="o">;</span> <span class="kt">double</span> <span class="n">b</span> <span class="o">=</span> <span class="mf">0.0008901234567876</span><span class="o">;</span> <span class="kt">double</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">-</span> <span class="n">b</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">c</span> <span class="o">==</span> <span class="mf">1.337</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Hallo doubles!&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Oh no! Comparison failed!&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . .</p> <h2>Solution</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Oh no! Comparison failed!</code></pre></div> <h2>Explanation</h2> <p>Doubles are internally represented using the <a href="http://en.wikipedia.org/wiki/IEEE_floating_point">IEEE 754 standard</a> (<a href="http://docs.oracle.com/javase/specs/jls/se7/html/jls-4.html">source</a>). This means, doubles are not represented with arbitrary precision.</p> <p>Just execute this snippet:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">a</span> <span class="o">=</span> <span class="mf">1.3378901234567876</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;a = &quot;</span> <span class="o">+</span> <span class="n">a</span><span class="o">);</span> <span class="kt">double</span> <span class="n">b</span> <span class="o">=</span> <span class="mf">0.0008901234567876</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;b = &quot;</span> <span class="o">+</span> <span class="n">b</span><span class="o">);</span> <span class="kt">double</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">-</span> <span class="n">b</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;c = &quot;</span> <span class="o">+</span> <span class="n">c</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">a</span> <span class="o">=</span> 1.3378901234567877 <span class="nv">b</span> <span class="o">=</span> 8.901234567876E-4 <span class="nv">c</span> <span class="o">=</span> 1.3370000000000002</code></pre></div> <h2>Resolve problem</h2> <p>Use an appropriate epsilon to compare floats/doubles:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">a</span> <span class="o">=</span> <span class="mf">1.3378901234567877</span><span class="o">;</span> <span class="kt">double</span> <span class="n">b</span> <span class="o">=</span> <span class="mf">0.0008901234567876</span><span class="o">;</span> <span class="kt">double</span> <span class="n">c</span> <span class="o">=</span> <span class="n">a</span> <span class="o">-</span> <span class="n">b</span><span class="o">;</span> <span class="kt">double</span> <span class="n">EPSILON</span> <span class="o">=</span> <span class="mf">0.000000000000001</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">Math</span><span class="o">.</span><span class="na">abs</span><span class="o">(</span><span class="n">c</span> <span class="o">-</span> <span class="mf">1.337</span><span class="o">)</span> <span class="o">&lt;</span> <span class="n">EPSILON</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Hallo doubles!&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Oh no! Comparison failed!&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> Übersicht der Pfeile in UML //martin-thoma.com/ubersicht-der-pfeile-in-uml/ Sat, 04 Aug 2012 09:23:29 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ubersicht-der-pfeile-in-uml <p>Folgende Pfeile werden in UML verwendet:</p> <h2>Klassendiagramme</h2> <h3>Vererbung</h3> <div style="width: 87px" class="wp-caption alignright"><a href="../images/2012/07/UML-vererbung.png"><img src="../images/2012/07/UML-vererbung.png" alt="Class B erbt von Class A; Class A ist die Oberklasse" width="" height="" class="size-full wp-image-32841 " /></a><p class="wp-caption-text">Class B erbt von Class A; Class A ist die Oberklasse</p></div> <p>Die <a href="http://de.wikipedia.org/wiki/Vererbung_(Programmierung)">Vererbung</a> ist eines der wichtigsten Prinzipien der objektorientierten Programmierung. Sie zeigt eine “ist ein”-Beziehung an.</p> <p>Beispiele sind:</p> <ul> <li><code>Tiger</code> ist eine <code>Gro&szlig;katze</code> ist eine <code>Katze</code> ist ein <code>Raubtier</code> ist ein <code>Tier</code>.</li> <li><code>Auto</code> ist ein <code>Fortbewegungsmittel</code>.</li> <li><code>Auto</code> ist ein <code>Luxusgut</code>.</li> </ul> <p>Beachte dass <code>Auto</code> hier sowohl von <code>Luxusgut</code>, als auch von <code>Fortbewegungsmittel</code> erbt. Das geht in manchen Programmiersprachen (C++, Python), in anderen nicht (Java).</p> <h3>Assoziation</h3> <div style="width: 87px" class="wp-caption alignright"><a href="../images/2012/07/UML-assoziation.png"><img src="../images/2012/07/UML-assoziation.png" alt="Assoziation" width="" height="" class="size-full wp-image-32901 " /></a><p class="wp-caption-text">Assoziation</p></div> <p>Die <a href="http://de.wikipedia.org/wiki/Assoziation_(UML)">Assoziation</a>zeigt eine Verbindung an, z.B.:</p> <ul> <li>Person - Termin: Eine Person hat Termine; Termine geh&ouml;ren zu einer Person.</li> <li>Lehrer - Sch&uuml;ler: Ein Sch&uuml;ler hat Lehrer; Lehrer haben Sch&uuml;ler.</li> <li>Auto - Fahrer: Ein Auto hat einen Fahrer; ein Fahrer hat ein Auto.</li> </ul> <p>In einer Datenbank würde man für diese Relationen eine weitere Tabelle erstellen. Also eine Tabelle für Personen, eine für Termine und eine für Person-Termin-Verknüpfungen.</p> <h3>Aggregation</h3> <div style="width: 87px" class="wp-caption alignright"><a href="../images/2012/07/UML-aggregation.png"><img src="../images/2012/07/UML-aggregation.png" alt="Aggregation" width="" height="" class="size-full wp-image-32871 " /></a><p class="wp-caption-text">Aggregation</p></div> <p>Die <a href="http://de.wikipedia.org/wiki/Assoziation_(UML)#Aggregation">Aggregation</a> ist eine spezielle Assoziation. Sie zeigt eine “hat”-Beziehung an. Dabei ist die Richtung wichtig und sollte angezeigt werden.</p> <p>Aggregationen sind z.B.:</p> <ul> <li>PKW hat R&auml;der</li> <li>Eltern haben Kinder</li> <li>Buchladen hat B&uuml;cher</li> </ul> <h3>Komposition</h3> <div style="width: 87px" class="wp-caption alignright"><a href="../images/2012/07/UML-komposition.png"><img src="../images/2012/07/UML-komposition.png" alt="Komposition" width="" height="" class="size-full wp-image-32891 " /></a><p class="wp-caption-text">Komposition</p></div> <p>Die <a href="http://de.wikipedia.org/wiki/Komposition_(UML)#Komposition">Komposition</a> zeigt eine notwendige “ist-Teil-von” Beziehung an. Das Teil kann also nicht ohne das Ganze existieren.</p> <p>Beispiele sind:</p> <ul> <li>Buch hat Buchseiten (Buchseiten gibt es nicht ohne Buch)</li> <li>Rechnung hat Posten (Rechnungsposten gibt es nicht ohne Rechnung)</li> <li>Graph hat Knoten (Knoten gibt es nicht ohne Graph)</li> </ul> <h3>Weitere</h3> <ul> <li>Die Benutzt-Relation wird als gestrichelter Pfeil mit nicht-ausgef&uuml;lltem Kopf dargestellt.</li> <li>Eine Implementierung wird als gestrichelter Pfeil mit rundem, nicht ausgef&uuml;lltem Kopf dargestellt.</li> </ul> <h2>Objektdiagramme</h2> <div style="width: 414px" class="wp-caption aligncenter"><a href="../images/2012/07/objektdiagramm-instance-of.png"><img src="../images/2012/07/objektdiagramm-instance-of.png" alt="UML: instanceOf beziehung in einem Objektdiagramm" width="" height="" class="size-full wp-image-36561" /></a><p class="wp-caption-text">UML: instanceOf beziehung in einem Objektdiagramm</p></div> <h2>Sequenzdiagramme</h2> <p><a href="http://de.wikipedia.org/wiki/Sequenzdiagramm">Sequenzdiagramme</a> haben wieder eigene Pfeile.</p> <div style="width: 431px" class="wp-caption aligncenter"><a href="../images/2012/07/sequenzdiagram.png"><img src="../images/2012/07/sequenzdiagram.png" alt="UML Sequenzdiagramm" width="" height="" class="size-full wp-image-32951" /></a><p class="wp-caption-text">UML Sequenzdiagramm</p></div> <p>Der Pfeil mit der ausgefüllten Spitze ist eine Synchrone Nachricht, der gestrichelte mit der nicht-ausgefüllten Spitze ist eine Antwort und der durchgezogenen Pfeil mit der nicht-ausgefüllten Spitze ist eine asynchrone Nachricht. <strong>ACHTUNG</strong>: In der Vorlesung bei Herrn Prof. Tichy hat die Antwort (Folie 42) auch keinen ausgefüllten Kopf, im gegensatz zu dem hier gezeigtem Bild!</p> <h2>Siehe auch</h2> <ul> <li><a title="How to create UML class diagrams" href="../how-to-create-uml-class-diagrams/">How to create UML class diagrams</a></li> </ul> Java Puzzle #5: Parallel Programming, Part 2 //martin-thoma.com/java-puzzle-5-parallel-programming-part-2/ Fri, 03 Aug 2012 17:00:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-5-parallel-programming-part-2 <p>What is the output of the following script:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">test</span> { <span style="color:#088;font-weight:bold">public</span> <span style="color:#088;font-weight:bold">static</span> <span style="color:#339;font-weight:bold">int</span> globalVar; <span style="color:#088;font-weight:bold">public</span> <span style="color:#088;font-weight:bold">static</span> <span style="color:#339;font-weight:bold">void</span> main(<span style="color:#0a8;font-weight:bold">String</span><span style="color:#339;font-weight:bold">[]</span> args) { globalVar = <span style="color:#00D">1</span>; MyParallelClass a = <span style="color:#080;font-weight:bold">new</span> MyParallelClass(); MyParallelClass b = <span style="color:#080;font-weight:bold">new</span> MyParallelClass(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b).start(); <span style="color:#0a8;font-weight:bold">System</span>.out.println(globalVar); } } </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">MyParallelClass</span> <span style="color:#088;font-weight:bold">implements</span> java.lang.Runnable { <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">int</span> counter = <span style="color:#00D">0</span>; <span style="color:#007">@Override</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">void</span> run() { <span style="color:#080;font-weight:bold">if</span> (test.globalVar &gt; <span style="color:#00D">0</span>) { <span style="color:#080;font-weight:bold">for</span> (<span style="color:#339;font-weight:bold">int</span> i = <span style="color:#00D">0</span>; i &lt; <span style="color:#00D">1000000</span>; i++) { counter++; } test.globalVar--; } } } </pre></div> </div> </div> <p>. . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <p><code>0</code>, <code>1</code> or <code>-1</code>.</p> <h2>Explanaition</h2> <p>First the simple ones: <code>0</code> is the result you would expect. One thread executes and reduces <code>globalVar</code> to <code>0</code>, the other one does nothing and then <code>globalVar</code> gets printed.</p> <p>If the main program is faster than any of the two threads, it prints <code>1</code> before <code>globalVar</code> gets reduced.</p> <p>Now the most interesting one: <code>-1</code>. This is called a <a href="http://en.wikipedia.org/wiki/Race_condition">race condition</a>. You have to know that <code>globalVar--</code> is not an atomic operation. First you have to get the value, then you have to reduce it and after that you can save the value.</p> <p>This is an order of execution which would lead to a wrong value:</p> <table> <tr> <th>First Thread</th> <th>Second Thread</th> <th>test.globalVar</th> </tr> <tr> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">checks if (globalVar &gt; 0) looping ... looping ... execute test.globalVar--;</code></pre></div> </td> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">. checks if (globalVar &gt; 0) execute all four bytecode commands of &quot;test.globalVar--;&quot; .</code></pre></div> </td> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">1 1 0 -1</code></pre></div> </td> </tr> </table> <h2>Resolve this problem</h2> <ul> <li>Use <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Thread.html#join()">join()</a> if you don't want to get <code>1</code> as output.</li> <li>If you don't want to get <code>-1</code>, you should take a look at the keyword <a href="http://docs.oracle.com/javase/tutorial/essential/concurrency/locksync.html">synchronised</a>.</li> </ul> <h2>A side note</h2> <p>With <code>javap -c MyParallelClass</code> you can view the <a href="http://en.wikipedia.org/wiki/Java_bytecode">bytecode</a> of the class <code>MyParallelClass</code>. It looks like this:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">Compiled</span> <span class="n">from</span> <span class="s">&quot;MyParallelClass.java&quot;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">MyParallelClass</span> <span class="kd">extends</span> <span class="n">java</span><span class="o">.</span><span class="na">lang</span><span class="o">.</span><span class="na">Object</span> <span class="kd">implements</span> <span class="n">java</span><span class="o">.</span><span class="na">lang</span><span class="o">.</span><span class="na">Runnable</span><span class="o">{</span> <span class="kd">public</span> <span class="kt">int</span> <span class="n">counter</span><span class="o">;</span> <span class="kd">public</span> <span class="nf">MyParallelClass</span><span class="o">();</span> <span class="nl">Code:</span> <span class="mi">0</span><span class="o">:</span> <span class="n">aload_0</span> <span class="mi">1</span><span class="o">:</span> <span class="n">invokespecial</span> <span class="err">#</span><span class="mi">1</span><span class="o">;</span> <span class="c1">//Method java/lang/Object.&quot;&lt;init&gt;&quot;:()V</span> <span class="mi">4</span><span class="o">:</span> <span class="n">aload_0</span> <span class="mi">5</span><span class="o">:</span> <span class="n">iconst_0</span> <span class="mi">6</span><span class="o">:</span> <span class="n">putfield</span> <span class="err">#</span><span class="mi">2</span><span class="o">;</span> <span class="c1">//Field counter:I</span> <span class="mi">9</span><span class="o">:</span> <span class="k">return</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">run</span><span class="o">();</span> <span class="nl">Code:</span> <span class="mi">0</span><span class="o">:</span> <span class="n">getstatic</span> <span class="err">#</span><span class="mi">3</span><span class="o">;</span> <span class="c1">//Field test.globalVar:I</span> <span class="mi">3</span><span class="o">:</span> <span class="n">ifle</span> <span class="mi">38</span> <span class="mi">6</span><span class="o">:</span> <span class="n">iconst_0</span> <span class="mi">7</span><span class="o">:</span> <span class="n">istore_1</span> <span class="mi">8</span><span class="o">:</span> <span class="n">iload_1</span> <span class="mi">9</span><span class="o">:</span> <span class="n">ldc</span> <span class="err">#</span><span class="mi">4</span><span class="o">;</span> <span class="c1">//int 1000000</span> <span class="mi">11</span><span class="o">:</span> <span class="n">if_icmpge</span> <span class="mi">30</span> <span class="mi">14</span><span class="o">:</span> <span class="n">aload_0</span> <span class="mi">15</span><span class="o">:</span> <span class="n">dup</span> <span class="mi">16</span><span class="o">:</span> <span class="n">getfield</span> <span class="err">#</span><span class="mi">2</span><span class="o">;</span> <span class="c1">//Field counter:I</span> <span class="mi">19</span><span class="o">:</span> <span class="n">iconst_1</span> <span class="mi">20</span><span class="o">:</span> <span class="n">iadd</span> <span class="mi">21</span><span class="o">:</span> <span class="n">putfield</span> <span class="err">#</span><span class="mi">2</span><span class="o">;</span> <span class="c1">//Field counter:I</span> <span class="mi">24</span><span class="o">:</span> <span class="n">iinc</span> <span class="mi">1</span><span class="o">,</span> <span class="mi">1</span> <span class="mi">27</span><span class="o">:</span> <span class="k">goto</span> <span class="mi">8</span> <span class="mi">30</span><span class="o">:</span> <span class="n">getstatic</span> <span class="err">#</span><span class="mi">3</span><span class="o">;</span> <span class="c1">//Field test.globalVar:I</span> <span class="mi">33</span><span class="o">:</span> <span class="n">iconst_1</span> <span class="mi">34</span><span class="o">:</span> <span class="n">isub</span> <span class="mi">35</span><span class="o">:</span> <span class="n">putstatic</span> <span class="err">#</span><span class="mi">3</span><span class="o">;</span> <span class="c1">//Field test.globalVar:I</span> <span class="mi">38</span><span class="o">:</span> <span class="k">return</span> <span class="o">}</span></code></pre></div> <p>Some links to the reference: <a href="https://www.vmth.ucdavis.edu/incoming/Jasmin/ref--19.html">getstatic</a>, <a href="https://www.vmth.ucdavis.edu/incoming/Jasmin/ref--21.html">iconst_1</a>, <a href="https://www.vmth.ucdavis.edu/incoming/Jasmin/ref-_isub.html">isub</a>, <a href="https://www.vmth.ucdavis.edu/incoming/Jasmin/ref-putstati.html">putstatic</a></p> <p>The interesting part of the bytecode is:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="mi">30</span><span class="o">:</span> <span class="n">getstatic</span> <span class="err">#</span><span class="mi">3</span><span class="o">;</span> <span class="c1">//Field test.globalVar:I</span> <span class="mi">33</span><span class="o">:</span> <span class="n">iconst_1</span> <span class="mi">34</span><span class="o">:</span> <span class="n">isub</span> <span class="mi">35</span><span class="o">:</span> <span class="n">putstatic</span> <span class="err">#</span><span class="mi">3</span><span class="o">;</span> <span class="c1">//Field test.globalVar:I</span></code></pre></div> <p>You can see that the JVM has to execute 4 commands for <code>test.globalVar--;</code>.</p> <h2>See also</h2> <ul> <li><a href="http://docs.oracle.com/javase/tutorial/essential/concurrency/atomic.html">Atomic Access</a> in Java</li> <li><a href="http://docs.oracle.com/javase/7/docs/api/javax/management/monitor/Monitor.html">Class Monitor</a></li> <li><a href="http://docs.oracle.com/javase/specs/jvms/se7/html/jvms-6.html#jvms-6.5.monitorenter">monitorenter</a> and <a href="http://docs.oracle.com/javase/specs/jvms/se7/html/jvms-6.html#jvms-6.5.monitorexit">monitorexit</a></li> <li><a href="http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/package-summary.html">Package java.util.concurrent</a></li> </ul> Shortfilms, Part II //martin-thoma.com/shortfilms-part-ii/ Thu, 02 Aug 2012 23:59:53 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/shortfilms-part-ii <div class="info">Here is the first part "<a href="../shortfilms/">Shortfilms</a>".</div> <p>Here are some nice shortfilms in high quality. If you missed the first part, here is the article “<a href="../shortfilms/" title="Shortfilms">shortfilms</a>” (Part I).</p> <h2>The Last Train</h2> <iframe src="http://player.vimeo.com/video/31215588" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Mac 'n' Cheese</h2> <iframe src="http://player.vimeo.com/video/27127177" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Electroshock</h2> <iframe src="http://player.vimeo.com/video/29193046" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Mytho Logique</h2> <iframe src="http://player.vimeo.com/video/24258323" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Impossible Present</h2> <iframe src="http://player.vimeo.com/video/33352381?title=0&amp;byline=0&amp;portrait=0&amp;color=ffffff" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>The Tale Of Mr. R&ecirc;vus</h2> <iframe src="http://player.vimeo.com/video/27653079?title=0&amp;byline=0&amp;portrait=0&amp;color=ffffff" width="512" height="218" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Holy Sheep</h2> <iframe src="http://player.vimeo.com/video/24474457?title=0&amp;byline=0&amp;portrait=0&amp;color=ffffff" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Danger Planet</h2> <iframe src="http://player.vimeo.com/video/28043193?title=0&amp;byline=0&amp;portrait=0&amp;color=ffffff" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> SWT I Klausur //martin-thoma.com/swt-i-klausur/ Thu, 02 Aug 2012 20:16:12 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/swt-i-klausur <p>Für die Klausur in Softwaretechnik I 2012 bei Herrn Prof. Dr. Tichy sollte man Folgendes auf jeden Fall wissen:</p> <ul> <li>Wie lautet der Aufbau des Wasserfallmodells?</li> <li>Was ist ein Sequenzdiagramm und wie sieht es aus? &rarr; <a href="http://de.wikipedia.org/wiki/Sequenzdiagramm">Antwort</a></li> <li>Wozu dient ein Aktivit&auml;tsdiagramm und wie sieht es aus? &rarr; <a href="http://de.wikipedia.org/wiki/Aktivit%C3%A4tsdiagramm">Antwort</a></li> <li>Wozu dienen die 21 Entwurfsmuster? &rarr; Siehe <a href="http://www.jetpunk.com/user-quizzes/27013/entwurfsmuster">mein Spiel</a> und <a href="http://www.vincehuston.org/dp/patterns_quiz.html">weiteres Spiel</a></li> <li>Wie sehen die Strukturmuster der 21 Entwurfmuster aus? &rarr; Siehe Kapitel 3.5</li> <li>Was wird zuerst erstellt: Das Lastenheft oder das Pflichtenheft? &rarr; <a href="http://de.wikipedia.org/wiki/Lastenheft">Antwort</a></li> <li>Welche zwei M&ouml;glichkeiten gibt es in Java, um eine Aufgabe parallel auszuf&uuml;hren? Was sind die Vor- und Nachteile? &rarr; <a href="http://stackoverflow.com/a/11774135/562769">Antwort</a></li> <li>Wie nennt man die Schl&uuml;sselw&ouml;rter der Art <code>@Test</code>, <code>@Before</code> und <code>@BeforeClass</code>? Was bewirken diese Schl&uuml;sselw&ouml;rter in JUnit? &rarr; <a href="http://www.vogella.com/articles/JUnit/article.html#usingjunit_annotations">Antwort</a></li> <li>Wozu dient JFrame? &rarr; <a href="../how-to-use-swing/" title="Swing I: How to use Swing">Antwort</a></li> </ul> <h2>Hinweise</h2> <blockquote><ul> <li>In den 60 Minuten Bearbeitungszeit haben Sie keine Zeit zum "Probemalen" oder "in Sch&ouml;nschrift nochmal abschreiben" vom Schmierblatt. Wenn es irgendwie geht, schreiben Sie Ihre L&ouml;sung gleich in lesbarer (!) Reinschrift.</li> <li>Die Farben rot und gr&uuml;n d&uuml;rfen Sie nicht verwenden.</li> <li>Was mit Bleistift geschrieben oder nicht entzifferbar ist, werten wir nicht.</li> <li>Es sind keine Hilfsmittel erlaubt.</li> <li>Sie brauchen kein Papier mitzubringen.</li> </ul></blockquote> <p>Aus dem Mailman-Verteiler von Herrn Karcher.</p> <h2>Termine</h2> <p><strong>Datum</strong>: Montag, den 06.08.2012 um 14:00 Uhr<br /> <strong>Ort</strong>:<br /> A - E: HSaF (Geb. 50.35)<br /> F - K: Gerthsen (Geb. 30.21)<br /> L - Q: Benz (Geb. 10.21)<br /> R–S: Gaede (Geb. 30.22)<br /> T–Z: Daimler (Geb. 10.21)<br /></p> <p><strong>Dauer</strong>: 60 min.<br /> <strong>Punkte</strong>: 60<br /> <strong>Übungsschein</strong>: Noch nicht im <a href="https://studium.kit.edu">Studierendenportal</a> (Stand: 02.08.2012)<br /> <strong>Bonuspunkte</strong>: Gibt es nicht, oder?<br /> <strong>Sitzplatzverteilung</strong>: ?<br /></p> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Klausurergebnisse</h2> <div style="width: 810px" class="wp-caption aligncenter"><a href="../images/2012/08/swt-1-klausur.png"><img src="../images/2012/08/swt-1-klausur.png" alt="Klausurergebnisse f&uuml;r SWT I" width="" height="" class="size-full wp-image-39581" /></a><p class="wp-caption-text">Klausurergebnisse f&uuml;r SWT I</p></div> <p><strong>Klausureinsicht</strong>: Montag, den 13.08.2012 von 14:00 bis 16:00 Uhr, SR 348, Infobau</p> Nature by Numbers //martin-thoma.com/nature-by-numbers/ Thu, 02 Aug 2012 17:00:22 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/nature-by-numbers <iframe src="http://player.vimeo.com/video/9953368" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <p>A short movie inspired by numbers, geometry and nature.</p> Java Puzzle #4: Parallel Programming //martin-thoma.com/java-puzzle-4-parallel-programming/ Thu, 02 Aug 2012 11:00:36 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-4-parallel-programming <p>What is the output of the following Java Snippet:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">MyParallelClass</span> <span style="color:#088;font-weight:bold">implements</span> java.lang.Runnable { <span style="color:#088;font-weight:bold">public</span> <span style="color:#0a8;font-weight:bold">String</span> name; <span style="color:#088;font-weight:bold">public</span> myParallelTry(<span style="color:#0a8;font-weight:bold">String</span> name) { <span style="color:#950">this</span>.name = name; } <span style="color:#007">@Override</span> <span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">void</span> run() { <span style="color:#0a8;font-weight:bold">System</span>.out.println(name); } } </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">test</span> { <span style="color:#088;font-weight:bold">public</span> <span style="color:#088;font-weight:bold">static</span> <span style="color:#339;font-weight:bold">void</span> main(<span style="color:#0a8;font-weight:bold">String</span><span style="color:#339;font-weight:bold">[]</span> args) { MyParallelClass a = <span style="color:#080;font-weight:bold">new</span> MyParallelClass(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">A</span><span style="color:#710">&quot;</span></span>); MyParallelClass b = <span style="color:#080;font-weight:bold">new</span> MyParallelClass(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">B</span><span style="color:#710">&quot;</span></span>); MyParallelClass c = <span style="color:#080;font-weight:bold">new</span> MyParallelClass(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">C</span><span style="color:#710">&quot;</span></span>); MyParallelClass d = <span style="color:#080;font-weight:bold">new</span> MyParallelClass(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">D</span><span style="color:#710">&quot;</span></span>); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d).start(); <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d).start(); <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d).start(); <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c).start(); <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d).start(); } } </pre></div> </div> </div> <p>. . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <table> <tr> <th>First Try</th> <th>Second Try</th> <th>Third Try</th> </tr> <tr> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">A C B - D A B C - D A - C A C D B B D</code></pre></div> </td> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">A B C - D A B C - D A B C - D A B C D</code></pre></div> </td> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">A B C - D A B C - D A B C - D A B C D</code></pre></div> </td> </tr> </table> <h2>Explanation</h2> <p>If you start threads like this, you don’t get any guarantee that they will finish their execution in order. If you want them to execute in block of four, you could use <a href="http://docs.oracle.com/javase/7/docs/api/java/lang/Thread.html#join()">join()</a>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#088;font-weight:bold">public</span> <span style="color:#339;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">test</span> { <span style="color:#088;font-weight:bold">public</span> <span style="color:#088;font-weight:bold">static</span> <span style="color:#339;font-weight:bold">void</span> main(<span style="color:#0a8;font-weight:bold">String</span><span style="color:#339;font-weight:bold">[]</span> args) { myParallelTry a = <span style="color:#080;font-weight:bold">new</span> myParallelTry(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">A</span><span style="color:#710">&quot;</span></span>); myParallelTry b = <span style="color:#080;font-weight:bold">new</span> myParallelTry(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">B</span><span style="color:#710">&quot;</span></span>); myParallelTry c = <span style="color:#080;font-weight:bold">new</span> myParallelTry(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">C</span><span style="color:#710">&quot;</span></span>); myParallelTry d = <span style="color:#080;font-weight:bold">new</span> myParallelTry(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">D</span><span style="color:#710">&quot;</span></span>); <span style="color:#0a8;font-weight:bold">Thread</span> tA = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a); tA.start(); <span style="color:#0a8;font-weight:bold">Thread</span> tB = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b); tB.start(); <span style="color:#0a8;font-weight:bold">Thread</span> tC = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c); tC.start(); <span style="color:#0a8;font-weight:bold">Thread</span> tD = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d); tD.start(); <span style="color:#080;font-weight:bold">try</span> { tA.join(); tB.join(); tC.join(); tD.join(); } <span style="color:#080;font-weight:bold">catch</span> (<span style="color:#C00;font-weight:bold">InterruptedException</span> e) { e.printStackTrace(); } <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>); tA = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a); tA.start(); tB = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b); tB.start(); tC = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c); tC.start(); tD = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d); tD.start(); <span style="color:#080;font-weight:bold">try</span> { tA.join(); tB.join(); tC.join(); tD.join(); } <span style="color:#080;font-weight:bold">catch</span> (<span style="color:#C00;font-weight:bold">InterruptedException</span> e) { e.printStackTrace(); } <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>); tA = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a); tA.start(); tB = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b); tB.start(); tC = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c); tC.start(); tD = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d); tD.start(); <span style="color:#080;font-weight:bold">try</span> { tA.join(); tB.join(); tC.join(); tD.join(); } <span style="color:#080;font-weight:bold">catch</span> (<span style="color:#C00;font-weight:bold">InterruptedException</span> e) { e.printStackTrace(); } <span style="color:#0a8;font-weight:bold">System</span>.out.println(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-</span><span style="color:#710">&quot;</span></span>); tA = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(a); tA.start(); tB = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(b); tB.start(); tC = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(c); tC.start(); tD = <span style="color:#080;font-weight:bold">new</span> <span style="color:#0a8;font-weight:bold">Thread</span>(d); tD.start(); <span style="color:#080;font-weight:bold">try</span> { tA.join(); tB.join(); tC.join(); tD.join(); } <span style="color:#080;font-weight:bold">catch</span> (<span style="color:#C00;font-weight:bold">InterruptedException</span> e) { e.printStackTrace(); } } } </pre></div> </div> </div> <table> <tr> <th>First Try</th> <th>Second Try</th> <th>Third Try</th> </tr> <tr> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">A B D C - A B C D - A B C D - A B C D</code></pre></div> </td> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">A B C D - A B C D - A B C D - A B C D</code></pre></div> </td> <td> <div class="highlight"><pre><code class="language-text" data-lang="text">A B C D - A B C D - A B C D - A B C D</code></pre></div> </td> </tr> </table> Python Puzzle #2: None and False //martin-thoma.com/python-puzzle-2-none-and-false/ Wed, 01 Aug 2012 17:00:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-puzzle-2-none-and-false <p>Python automatically casts to boolean if you use another type of variable for a boolean expression.</p> <p>Here is an example:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">if</span> <span class="p">[</span><span class="mi">1</span><span class="p">]:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Crazy, &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="mi">1</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;this &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="mi">2</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;is &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="bp">True</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;also &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="s">&quot;a string&quot;</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;true.&quot;</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;&quot;</span><span class="p">)</span> <span class="k">if</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;This &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="ow">not</span> <span class="bp">False</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;is &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="ow">not</span> <span class="mi">0</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;not &quot;</span><span class="p">)</span> <span class="k">if</span> <span class="ow">not</span> <span class="p">[]:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;true.&quot;</span><span class="p">)</span></code></pre></div> <p>Everything gets printed.</p> <p>Now the riddle. What is the output of the following script:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">if</span> <span class="bp">None</span> <span class="o">==</span> <span class="bp">False</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;None is false.&quot;</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;None and false are not equal.&quot;</span><span class="p">)</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">None and <span class="nb">false </span>are not equal.</code></pre></div> <h2>Explanation</h2> <p>Although <code>None</code> and <code>False</code> evaluate to <code>False</code> if they are used in a boolean expression, <code>None</code> is not the same as <code>False</code>.</p> How to write music with LaTeX //martin-thoma.com/how-to-write-music-with-latex/ Wed, 01 Aug 2012 10:45:49 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-write-music-with-latex <p>It is possible to write music with LaTeX. My girlfriend was quite surprised of this, so I decided to <del datetime="2012-08-01T08:01:06+00:00">write a little tutorial</del> show some examples.</p> <h2>Symbols</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/music-notes.png"><img src="../images/2012/08/music-notes.png" alt="Some basic music symbols" width="" height="" class="size-full wp-image-37171" /></a><p class="wp-caption-text">Some basic music symbols</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{wasysym} \begin{document} \eighthnote ~~~ \halfnote ~~~ \twonotes ~~~ \fullnote ~~~ \quarternote ~~~ $\natural$ ~~~ $\flat$ ~~~ $\sharp$ \end{document} </pre></div> </div> </div> <p>The harmony package offers some additional symbols:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/latex-music-harmony.png"><img src="../images/2012/08/latex-music-harmony.png" alt="music symbols form the LaTeX-harmony package" width="" height="" class="size-full wp-image-37181" /></a><p class="wp-caption-text">music symbols form the LaTeX-harmony package</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{harmony} \begin{document} \noindent \AAcht ~~~ \Acht ~~~ \AchtBL ~~~ \AchtBR ~~~ \AcPa \\ \DD ~~~ \DDohne ~~~ \Dohne ~~~ \Ds ~~~ \DS \\ \Ganz ~~~ \GaPa ~~~ \Halb ~~~ \HaPa ~~~ \Pu ~~~ \Sech \\ \SechBL ~~~ \SechBl ~~~ \SechBR ~~~ \SePa ~~~ \UB ~~~ \Vier \\ \ViPa ~~~ \VM ~~~ \Zwdr ~~~ \ZwPa \end{document} </pre></div> </div> </div> <h2>musixtex</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/08/latex-musixtex.png"><img src="../images/2012/08/latex-musixtex.png" alt="musixtex example" width="" height="" class="size-full wp-image-37221" /></a><p class="wp-caption-text">musixtex example</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{musixtex} \begin{document} \noindent This is a clef: \begin{music}\trebleclef\end{music} - a simple example\\ for the \LaTeX{} package musixtex. \end{document} </pre></div> </div> </div> <h2>ABC</h2> <h3>Preparation</h3> <p>You have to have ABC installed. For Ubuntu-Users:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install abcm2ps </pre></div> </div> </div> <h3>Example</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper]{article} \usepackage{abc} \begin{document} You can create music sheets within the abc-environment: \begin{abc}[name=c-dur] X: 1 % start of header K: C % scale: C major &quot;Text&quot;c2 G4 | (3FED c4 G2 | \end{abc} \end{document} </pre></div> </div> </div> <p>compile with</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pdflatex --shell-escape myTexFile.tex </pre></div> </div> </div> <p>to get this:</p> <div style="width: 487px" class="wp-caption aligncenter"><a href="../images/2012/07/abc-example.png"><img src="../images/2012/07/abc-example.png" alt="ABC example for creating music sheets with LaTeX" width="" height="" class="size-full wp-image-33701" /></a><p class="wp-caption-text">ABC example for creating music sheets with LaTeX</p></div> <h2>LilyPond</h2> <h3>Preparation</h3> <p>Make sure that you have installed <a href="http://en.wikipedia.org/wiki/GNU_LilyPond">GNU LilyPond</a> and LaTeX.</p> <p>Ubuntu-Users have to type</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install lilypond </pre></div> </div> </div> <p>to install Lilypond.</p> <h3>Example</h3> <h4>From the Documentation</h4> <p>Save the following source as <code>lilybook.lytex</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper]{article} \begin{document} Documents for \verb+lilypond-book+ may freely mix music and text. For example, \begin{lilypond} \relative c' { c2 g'2 \times 2/3 { f8 e d } c'2 g4 } \end{lilypond} Options are put in brackets. \begin[fragment,quote,staffsize=26,verbatim]{lilypond} c'4 f16 \end{lilypond} Larger examples can be put into a separate file, and introduced with \verb+\lilypondfile+. \end{document} </pre></div> </div> </div> <p>Compile it with these commands:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>lilypond-book --output=out --pdf lilybook.lytex cd out/ pdflatex lilybook mv lilybook.pdf ../lilybook.pdf cd .. rm -rf out </pre></div> </div> </div> <p>For simplification, you can save this as <code>compile.sh</code>, execute <code>chmod +x compile.sh</code> and now you only have to enter <code>./compile.sh</code> to generate the PDF.</p> <p>Output:</p> <div style="width: 604px" class="wp-caption aligncenter"><a href="../images/2012/07/lilypond-example.png"><img src="../images/2012/07/lilypond-example.png" alt="Lilypond example - output was a PDF" width="" height="" class="size-full wp-image-33661" /></a><p class="wp-caption-text">Lilypond example - output was a PDF</p></div> <h2>Further Reading</h2> <ul> <li>ABC <ul> <li><a href="http://www.tug.org/texlive/Contents/live/texmf-dist/doc/latex/abc/abc.pdf">ABC-environment Documentation</a></li> </ul> </li> <li>LilyPond <ul> <li><a href="http://lilypond.org/doc/v2.14/Documentation/learning/index#top">LilyPond &mdash; Learning Manual</a></li> <li><a href="http://lilypond.org/doc/v2.14/Documentation/essay.pdf">Lilypond 2.14 Documentation</a></li> <li><a href="http://createdigitalmusic.com/2010/05/lilypond-free-beautiful-music-notation-engraving-for-anyone/">Lilypond: Free, Beautiful Music Notation Engraving for Anyone</a> by Peter Kirn</li> <li><a href="http://stackoverflow.com/q/10152486/562769">Including Lilypond in LaTeX</a></li> <li><a href="http://tex.stackexchange.com/a/69804/5645">Beautiful example</a></li> </ul> </li> <li><a href="http://tex.stackexchange.com/questions/19813/creating-a-custom-songbook-with-the-songs-package">Creating a custom songbook with the songs package</a></li> <li><a href="http://homepage2.nifty.com/tonomu/score/musixtex/musixtexe.html">MusiXTeX</a></li> </ul> <p>If you’ve made some more complex examples with LaTeX, I’d be happy if you added them in the comments.</p> Die Länder der Erde //martin-thoma.com/die-lander-der-erde/ Tue, 31 Jul 2012 17:00:57 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/die-lander-der-erde <div style="width: 492px" class="wp-caption aligncenter"><a href="../images/2012/07/laender-der-erde.png"><img src="//martin-thoma.com/captions/laender-der-erde-2.png" alt="L&auml;nder der Erde" width="482" height="280" class=" wp-image-35581 " /></a><p class="wp-caption-text">L&auml;nder der Erde</p></div> <p>Hier ist ein <a href="http://www.jetpunk.com/quizzes/lander-der-welt-quiz">Spiel</a>, bei dem man die Länder der Erde eingeben muss. Es ist schon erschreckent, wie viele weiße Flecken hier sind.</p> <h2>Punktzahl</h2> <h3>26. Juli 2012</h3> <p>You scored 54/196 = 28%. This beats or equals 21.1% of test takers. The average score is 93.</p> <p>Viele afrikanische Länder sind mir unbekannt. Habt ihr schon mal von <a href="http://de.wikipedia.org/wiki/Nauru">Nauru</a> oder <a href="http://de.wikipedia.org/wiki/Kiribati">Kiribati</a> gehört?</p> <h3>02. August 2012</h3> <p>You scored 90/196 = 46%. This beats or equals 67.6% of test takers. The average score is 77. Your high score is 90.</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/07/laender-der-erde-2.png"><img src="../images/2012/07/laender-der-erde-2.png" alt="L&auml;nder der Erde - zweiter Versuch" width="" height="" class="size-full wp-image-37601" /></a><p class="wp-caption-text">L&auml;nder der Erde - zweiter Versuch</p></div> B-Bäume //martin-thoma.com/b-baume/ Fri, 27 Jul 2012 19:53:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/b-baume <p>Ein B-Baum ist eine Datenstruktur, die vor allem für Datenbanken (z.B. <a href="http://de.wikipedia.org/wiki/SQLite">SQLite</a>) und Dateisysteme (z.B. <a href="http://de.wikipedia.org/wiki/Ext3">ext3</a>) eingesetzt wird.</p> <p>Im Folgenden sollte man immer im Hinterkopf behalten, dass an den Schlüsseln auch Werte - sog. Satellitendaten - hängen. Der Einfachheit halber lasse ich diese aber hier weg.</p> <h2>Definition</h2> <p>Die folgende Definition ist sinngemäß aus “Introduction to Algorithms” von Thomas H. Cormen übernommen.</p> <p>Für einen <strong>B-Baum der Ordnung t</strong>, <code>$t \in \mathbb{N} \setminus \{1\}$</code>, gilt:</p> <ol> <li>Jeder Knoten `$x$` hat die folgenden Attribute: <ol> <li>`$n$`, die Anzahl der Schl&uuml;ssel die im Knoten `$x$` gespeichert wird,</li> <li>die `$n$` Schl&uuml;ssel, die in aufsteigender Reihenfolge gespeichert werden (also `$key_1 \leq key_2 \leq ... \leq key_{n}$`),</li> <li>`$isLeaf$`, ein boolscher Wert der <code>True</code> ist, falls `$x$` ein Blatt ist und <code>False</code> ist, falls `$x$` ein innerer Knoten ist</li> </ol> </li> <li>Jeder innere Knoten hat `$n + 1$` Zeiger `$c_1, c_2, ... c_{n+1}$` auf seine Kinder. Blattknoten haben keine Kinder, also sind ihre `$c_i$`-Attribute undefiniert.</li> </ol> <p>Ein Knoten eines B-Baumes sieht also so aus:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-node.png"><img src="../images/2012/07/b-tree-node.png" alt="Node of a B-tree" width="" height="" class="size-full wp-image-35861" /></a><p class="wp-caption-text">Node of a B-tree</p></div> <p>&lt;ol start=3&gt;</p> <li>Die Schl&uuml;ssel `$key_i$` setzen grenzen f&uuml;r die Werte der Schl&uuml;ssel, die in den einzelnen Subb&auml;umen gespeichert sind.<br /> Falls `$k_i$` ein Schl&uuml;ssel im Subbaum mit der Wurzel `$c_i$` ist, dann gilt: `$k_1 \leq key_1 \leq k_2 \leq key_2 \leq ... \leq key_{n} \leq k_{n} \leq key_{n+1}$`</li> <li>Alle Bl&auml;tter haben die gleiche Tiefe.</li> <li>F&uuml;r die Anzahl der Schl&uuml;ssel eines Knotens gilt: <ol> <li>Jeder Knoten (bis auf die Wurzel) hat mindestens t-1 Schl&uuml;ssel.</li> <li>Jeder Knoten hat h&ouml;chstens `$2t - 1$` Schl&uuml;ssel.</li> </ol> </li> <p>&lt;/ol&gt;</p> <h2>Stolperfallen</h2> <p>Ein Schlüssel ist etwas anderes als ein Zeiger!</p> <h2>Folgerungen</h2> <ul> <li>`$(2) \Rightarrow$` Die Wurzel hat min. 2 Kinder, falls der Baum nicht leer ist.</li> <li>`$(2), (5.1) \Rightarrow$` Jeder innere Knoten (bis auf die Wurzel) hat min. t Kinder.</li> <li>`$(2), (5.2) \Rightarrow$` Jeder innere Knoten hat maximal 2t Kinder.</li> <li>Wenn man an den Zeigern die Kinder in die Elterknoten zieht, sodass am Ende alle Knoten in der Wurzel sind, entsteht wegen (3) eine sortierte Liste.</li> <li>`$ h \leq \log_t \frac{n+1}{2}$` (Cormen, S. 489)</li> <li>Ein B-Baum hat in der Tiefe h min. `$2t^{h-1}$` Knoten.</li> </ul> <h2>Besondere B-B&auml;ume</h2> <p>Ein B-Baum der Ordnung t = 2 wird auch <a href="http://de.wikipedia.org/wiki/2-3-4-Baum">2-3-4-Baum</a> genannt, da jeder Knoten entweder 2, 3 oder 4 Kinder hat.</p> <p>Ich habe ja ausgeschlossen, dass es einen B-Baum der Ordnung t = 1 gibt. Warum eigentlich? Aus (5.1) folgt: In einem B-Baum der Ordnung t = 1 müssten einzelne Knoten keine Schlüssel haben. Das ist nicht sinnvoll. Also muss <code>$t \geq 2$</code> gelten.</p> <h2>Suchen eines Schl&uuml;ssels</h2> <p>Das Suchen eines Schlüssels funktioniert so:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">SEARCH</span><span class="o">-</span><span class="n">KEY</span><span class="p">(</span><span class="n">node</span><span class="p">,</span> <span class="n">key</span><span class="p">):</span> <span class="nb">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">while</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">node</span><span class="o">.</span><span class="n">n</span> <span class="ow">and</span> <span class="n">node</span><span class="o">.</span><span class="n">key</span><span class="p">[</span><span class="n">i</span><span class="p">]</span><span class="o">.</span><span class="n">key</span> <span class="o">&lt;</span> <span class="n">key</span><span class="p">:</span> <span class="n">i</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">if</span> <span class="n">node</span><span class="o">.</span><span class="n">key</span><span class="p">[</span><span class="n">i</span><span class="p">]</span><span class="o">.</span><span class="n">key</span> <span class="o">==</span> <span class="n">key</span><span class="p">:</span> <span class="c"># Schl&amp;uuml;ssel ist gesuchter Schl&amp;uuml;ssel</span> <span class="k">return</span> <span class="n">node</span><span class="o">.</span><span class="n">key</span><span class="p">[</span><span class="n">i</span><span class="p">]</span><span class="o">.</span><span class="n">satelittendaten</span> <span class="k">else</span> <span class="k">if</span> <span class="n">node</span><span class="o">.</span><span class="n">isLeaf</span><span class="p">:</span> <span class="c"># Erfolglose Suche</span> <span class="k">return</span> <span class="n">NIL</span> <span class="k">else</span><span class="p">:</span> <span class="c"># Rekursiv weitersuchen</span> <span class="n">DISK</span><span class="o">-</span><span class="n">READ</span><span class="p">(</span><span class="n">node</span><span class="o">.</span><span class="n">c</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="k">return</span> <span class="n">SEARCH</span><span class="o">-</span><span class="n">KEY</span><span class="p">(</span><span class="n">node</span><span class="o">.</span><span class="n">c</span><span class="p">[</span><span class="n">i</span><span class="p">],</span> <span class="n">key</span><span class="p">)</span></code></pre></div> <p>Es wird also zuerst der Knoten durchsucht und dann gegebenenfalls der passende Subbaum.</p> <p>Laut Vorlesung (Folie 97) gilt:</p> <ul> <li>Anzahl Zugriffe auf Hintergrundspeicher maximal: `${\cal O}(\log_t(n))$`</li> <li>Innerhalb eines Knotens: `${\cal O}(t)$`</li> <li>Insgesamt also: `${\cal O}(t \cdot \log_t(n))$`</li> </ul> <h2>Einf&uuml;gen von Schl&uuml;sseln</h2> <p>Wenn ein Schlüssel in einen B-Baum eingefügt werden soll, dann muss man insebesondere auf Regel (5.1) und (5.2) achten: Jeder Knoten enthält n Schlüssel, mit <code>$t-1 \leq n \leq 2t -1$</code>.</p> <p>Die Idee ist, dass man das Blatt sucht, in dem der Schlüssel sein müsste. Falls noch Platz ist, kann man den Schlüssel einfach einfügen. Falls nicht, muss man das Blatt aufsplitten.</p> <h3>Beispiel zu Fall 1: Es ist noch Platz</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-2-small.png"><img src="../images/2012/07/b-tree-2-small.png" alt="B-Baum der Ordnung t = 2" width="" height="" class="size-full wp-image-36091" /></a><p class="wp-caption-text">Abb. 2: B-Baum der Ordnung t = 2</p></div> <p>In den B-Baum aus Abb. 2 soll nun der Schlüssel <code>16</code> eingefügt werden. In einem B-Baum der Ordnung 2 hat jeder Knoten mindestens einen und höchstens 3 Schlüssel. Egal wo wir also landen würden, es würde noch in diesen Baum passen. Wir landen aber im Knoten rechts unten, da <code>$11 &lt; 16$</code> ist.</p> <p>Das Ergebnis ist also:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-2-small-2.png"><img src="../images/2012/07/b-tree-2-small-2.png" alt="B-Baum der Ordnung t = 2" width="" height="" class="size-full wp-image-36111" /></a><p class="wp-caption-text">Abb. 3: B-Baum der Ordnung t = 2</p></div> <h3>Beispiel zu Fall 2: Knoten&uuml;berlauf</h3> <p>Will man nun in den B-Baum der Ordnung 2 aus Abb. 3 den Schlüssel 17 hinzufügen, so gibt es einen “Knotenüberlauf”. Der Schlüssel müsste in den Knoten rechts unten. Damit hätte dieser 4 Schlüssel, er darf aber nur 3 haben. Also splitten wir zuerst den Knoten. Schlüssel 15 wandert zu dem Elternknoten hoch, die beiden einzelnen Schlüssel bilden eigene Knoten. Damit man sieht, was mit den Schlüsseln geschehen würde, wenn der Baum größer wäre, habe ich diese mal eingefärbt:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-2-small-3.png"><img src="../images/2012/07/b-tree-2-small-3.png" alt="Abb. 4: B-Baum der Ordnung t = 2" width="" height="" class="size-full wp-image-36131" /></a><p class="wp-caption-text">Abb. 4: B-Baum der Ordnung t = 2</p></div> <p>Nun ist man beim Einfügen von 17 wieder in Fall 1. Das Ergebnis sieht so aus:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-2-small-4.png"><img src="../images/2012/07/b-tree-2-small-4.png" alt="B-Baum der Ordnung t = 2" width="" height="" class="size-full wp-image-36151" /></a><p class="wp-caption-text">Abb. 5: B-Baum der Ordnung t = 2</p></div> <p>Natürlich kann es auch passieren, dass beim hochwandern des mittleren Knoten (15 von Abb. 3 nach Abb. 4) der Elternknoten überläuft. Dann muss halt auch dieser gesplittet werden. Wenn die Wurzel überläuft, muss eine neue Wurzel erstellt werden. Dann kann die alte Wurzel gesplittet werden.</p> <p>Die Laufzeit des Einfügens ist in <code>${\cal O}(t \cdot \log_t(n))$</code>.</p> <h2>L&ouml;schen eines Schl&uuml;ssels</h2> <p>Falls sich der Schlüssel in einem Blatt befindet, kann man ihn einfach löschen. Allerdings muss man darauf achten, dass mindestens t-1 Schlüssel im Knoten verbleiben.</p> <p>Ist der Schlüssel in einem inneren Knoten ist das ganze schwerer.</p> <h3>Fall 1: Schl&uuml;ssel in Blatt</h3> <p>Der Einfachste Fall ist der <a href="#Beispiel_zu_Fall_1_Es_ist_noch_Platz">1. Fall des Einfügens</a>, nur umgekehrt. Also aus dem B-Baum aus Abb. 3 die 16 entfernen. Dann entsteht der B-Baum aus Abb. 2.</p> <h3>Fall 2 - 3</h3> <p>Für die anderen Fälle habe ich leider kein kleines Beispiel und will deshalb auf die Erklärung verzichten.</p> <p>Falls ihr da Hilfe braucht: Cormen, dritte Ausgabe, S. 499ff war sehr hilfreich. (<a href="http://shafaetsplanet.com/uploads/pdf/Introduction%20to%20Algorithms.pdf">Link</a> - Warum auch immer der eine PDF-Datei vom Buch hat. Die KIT-Bibliothek hat leider keine Online-Version.)</p> <h2>Trivia</h2> <blockquote>[...] standard B-trees had numerous characteristics that were at odds with the ext2 design philosophy of simplicity and robustness. For example, XFS's B-tree implementation was larger than all of ext2 or ext3's source files combined.</blockquote> <p>Source: <a href="http://ext2.sourceforge.net/2005-ols/paper-html/node3.html">ext2.sourceforge.net</a></p> <h2>Beispiel</h2> <p>Fügt man die Schlüssel 2, 4, 6, 8, 10, 12 in einen anfangs leeren B-Baum ein, entwickelt sich dieser wie folgt:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-3-evolution.png"><img src="../images/2012/07/b-tree-3-evolution.png" alt="Entwicklung eines B-Baumes der Ordnung t = 3" width="" height="" class="size-full wp-image-36421" /></a><p class="wp-caption-text">Entwicklung eines B-Baumes der Ordnung t = 3</p></div> <p>Die grauen Felder sind für Zeiger reserviert. Ist kein Zeiger eingezeichnet, dann ist es ein NIL-Zeiger.</p> <h2>Siehe auch</h2> <ul> <li><a href="http://stackoverflow.com/questions/11684578/which-datastructure-do-nodes-of-b-trees-use">Which datastructure do nodes of B-Trees use?</a></li> <li><a href="http://stackoverflow.com/questions/32376/what-is-a-good-open-source-b-tree-implementation-in-c">What is a good open source B-tree implementation in C?</a> - Da kann man mal sehen wie es wirklich funktioniert ☺</li> <li><a href="http://stackoverflow.com/a/6403383/562769">Red Black Tree vs. B Tree</a></li> <li><a href="http://stackoverflow.com/a/1589587/562769">When to choose RB tree, B-Tree or AVL tree?</a></li> </ul> Die Landau-Symbole //martin-thoma.com/die-landau-symbole/ Thu, 26 Jul 2012 08:41:08 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/die-landau-symbole <h2>Definitionen</h2> <p><code>$ \begin{eqnarray*} {\cal O}(g(n)) &amp;:= \{f(n) | \exists_{c &gt; 0} \exists_{n_0 &gt; 0} \forall_{n \geq n_0}: f(n) &lt; c \cdot g(n) \} \\ {\cal o}(g(n)) &amp;:= \{f(n) | \forall_{c &gt; 0} \exists_{n_0 &gt; 0} \forall_{n \geq n_0}: f(n) &lt; c \cdot g(n) \} \\ \Omega (g(n)) &amp;:= \{f(n) | \exists_{c &gt; 0} \exists_{n_0 &gt; 0} \forall_{n \geq n_0}: f(n) &gt; c \cdot g(n) \} \\ \omega (g(n)) &amp;:= \{f(n) | \forall_{c &gt; 0} \exists_{n_0 &gt; 0} \forall_{n \geq n_0}: f(n) &gt; c \cdot g(n) \} \\ \end{eqnarray*} $</code> <code>$\Theta (g(n)) := \{f(n) | \exists_{c_0 &gt; 0} \exists_{c_1 &gt; 0} \exists_{n_0 &gt; 0} \forall_{n &gt; n_0}: c_0 \cdot g(n) &lt; f(n) &lt; c_1 \cdot g(n) \}$</code></p> <h2>Wichtige Aussagen der Mengen</h2> <p><code>$\begin{align} f(n) \in {\cal O}(g(n)) &amp;\Leftrightarrow g(n) \in \Omega(f(n)) \\ f(n) \in {\cal o}(g(n)) &amp;\Leftrightarrow g(n) \in \omega(f(n)) \\ f(n) \in {\cal O}(g(n)) \land f(n) \in \Omega(g(n)) &amp;\Leftrightarrow f(n) \in \Theta(g(n)) \\ f(n) \in o(g(n)) &amp;\Leftrightarrow \lim \frac{f(n)}{g(n)} = 0 \\ f(n) \in \Theta ( g(n)) &amp;\Leftrightarrow g(n) \in \Theta(f(n)) \\ f(n) \in \omega(g(n)) &amp;\Leftrightarrow \lim \frac{g(n)}{f(n)} = 0 \end{align}$</code></p> <h2>Logarithmusgesetze</h2> <p><code>$ \begin{align} \log(x \cdot y) &amp;= \log(x) + \log(y) \\ \log(\frac{x}{y}) &amp;= \log(x) &amp;ndash; \log(y) \\ \log(x^r) &amp;= r \cdot \log(x) \end{align}$</code></p> <h2>Wichtige Beziehungen von Funktionen</h2> <p><code>${\cal O}(1) \subsetneq {\cal O}(\log n) \subsetneq {\cal O}(n) \subsetneq {\cal O}(n^{2.1}) \subsetneq {\cal O} \subsetneq (n^{2.2}) {\cal O}(n^{100}) \subsetneq {\cal O}(n!) \subsetneq {\cal O}(2^n)$</code> <code>${\cal O}(2^n) \subsetneq {\cal O}(2^{2n}) \subsetneq {\cal O}(3^n) \subsetneq {\cal O}(n^n) \subsetneq {\cal O}(n^{(n^2)}) \subsetneq$</code></p> <h2>Beispiele</h2> <p>Im Folgenden gelte immer: <code>$f: \mathbb{N} \rightarrow \mathbb{R^+}$</code> und <code>$g:\mathbb{N} \rightarrow \mathbb{R^+}$</code></p> <h3>Nummer 1</h3> <p><strong>Voraussetzungen</strong>: Sei <code>$f(n) := \sqrt{2}^{\lg(n)}$</code> und <code>$g(n) := n \cdot \lg(n)$</code>. <strong>Behauptung</strong>: <code>$f \in {\cal O}(g(n))$</code> <strong>Beweis</strong>: <code>$f(n) = \sqrt{2}^{\lg(n)} = 10^{\lg(\sqrt{2}^{\lg(n)})} = 10^{\lg(\sqrt{2}) \cdot \lg(n)} = n^{\lg(\sqrt{2})}= n^{\frac{1}{2} \cdot \lg(2)} &lt; n^1 = n$</code></p> <p>Es gilt: <code>$n \in {\cal O}(n \cdot \lg(n)) = {\cal O}(g(n))$</code> <code>$\Rightarrow f(n) \in {\cal O}(g(n)) \blacksquare$</code></p> <h3>Nummber 2</h3> <p><strong>Voraussetzungen</strong>: Sei <code>$f(n) := \sqrt{5}^{\log_3(n)}$</code> und <code>$g(n) := n^2$</code>. <strong>Behauptung</strong>: <code>$f \in {\cal o}(g(n))$</code> <strong>Beweis</strong>: <code>$f(n) = \sqrt{5}^{\log_3(n)} = 3^{\log_3(\sqrt{5}^{\log_3(n)})} = 3^{\log_3(5) \cdot \log_3(n)} = n^{\log_3(5)} &lt; n^{\log_3(9)} = n^{\log_3(3^2)} = n^2$</code></p> <p>Sei <code>$\varepsilon &gt; 0$</code>. Dann gilt: <code>$n^{2- \varepsilon} \in o(n^2) \Rightarrow f(n) \in o(g(n)) \blacksquare$</code></p> Plotting graphs with PGFplots (LaTeX and Tikz) //martin-thoma.com/plotting-graphs-with-pgfplots-latex-and-tikz/ Tue, 24 Jul 2012 17:00:28 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/plotting-graphs-with-pgfplots-latex-and-tikz <p>I guess many of you might need to plot functions or data once. So I’ve made one example that shows much of the features you might need:</p> <ul> <li>You can see how to change the axis' from normal linear scale to logarithmic scale.</li> <li>Some axis-manipulations were used.</li> <li>I have used a CSV-file to import and plot data.</li> <li>The red line was drawn with a mathematical function.</li> </ul> <p>Best of all: I didn’t use anything which is not in LaTeX ☺ (Well, the generation of the CSV-file doesn’t count. I just wanted to include such an example for physicists who might need to plot results of experiments).</p> <p>The complete source is in the <a href="../images/2012/07/birthday-paradox.zip">Birthday Paradox Archive</a>.</p> <h2>Result</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/birthday-paradox.png"><img src="../images/2012/07/birthday-paradox.png" alt="Plot of the birthday paradox" width="" height="" class="size-full wp-image-34821" /></a><p class="wp-caption-text">Plot of the birthday paradox</p></div> <h2>LaTeX-Code</h2> <p>The following LaTeX-Code used TikZ and PGFplots:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>% Plot of the probability that two people out of n people have the % same birthday. % Author: Martin Thoma % Source: ../plotting-graphs-with-pgfplots/ \documentclass{article} \usepackage[pdftex,active,tightpage]{preview} \setlength\PreviewBorder{2mm} \usepackage{pgfplots} \usepackage{tikz} \usetikzlibrary{arrows, positioning, calc} \begin{document} \begin{preview} \begin{tikzpicture} \begin{axis}[ width=15cm, height=8cm, % size of the image grid = major, grid style={dashed, gray!30}, %xmode=log,log basis x=10, %ymode=log,log basis y=10, xmin=0, % start the diagram at this x-coordinate xmax=62, % end the diagram at this x-coordinate ymin=0, % start the diagram at this y-coordinate ymax=1.1, % end the diagram at this y-coordinate /pgfplots/xtick={0,5,...,60}, % make steps of length 5 extra x ticks={23}, extra y ticks={0.507297}, axis background/.style={fill=white}, ylabel=probability of at least one birthday-collision, xlabel=people, tick align=outside] % import the correct data from a CSV file \addplot table [id=exp]{data.csv}; % mark x=23 \coordinate (a) at (axis cs:23,0.507297); \draw[blue, dashed, thick](a -| current plot begin) -- (a); \draw[blue, dashed, thick](a |- current plot begin) -- (a); % plot the stirling-formulae \addplot[domain=0:60, red, thick] {1-(365/(365-x))^(365.5-x)*e^(-x)}; \end{axis} \end{tikzpicture} \end{preview} \end{document} </pre></div> </div> </div> <p>I generate the images directly with this Makefile:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>SOURCE = birthday-paradox DELAY = 80 DENSITY = 300 WIDTH = 500 make: pdflatex $(SOURCE).tex -output-format=pdf make clean clean: rm -rf $(TARGET) *.class *.html *.log *.aux gif: pdfcrop $(SOURCE).pdf convert -verbose -delay $(DELAY) -loop 0 -density $(DENSITY) $(SOURCE)-crop.pdf $(SOURCE).gif make clean png: make make svg inkscape $(SOURCE).svg -w $(WIDTH) --export-png=$(SOURCE).png transparentGif: convert $(SOURCE).pdf -transparent white result.gif make clean svg: #inkscape $(SOURCE).pdf --export-plain-svg=$(SOURCE).svg pdf2svg $(SOURCE).pdf $(SOURCE).svg # Necessary, as pdf2svg does not always create valid svgs: inkscape $(SOURCE).svg --export-plain-svg=$(SOURCE).svg </pre></div> </div> </div> <h2>See also</h2> <ul> <li><a href="../plotting-function-graphs-with-latex/">Plotting function graphs with LaTeX</a></li> <li><a href="http://www.texample.net/tikz/examples/tag/plots/">Plotting examples</a></li> <li><a href="http://www.texample.net/tikz/examples/area/mathematics/">Mathematics examples</a></li> <li><a href="http://tex.stackexchange.com/questions/tagged/pgfplots?sort=votes">tex.stackexchange.com</a></li> </ul> Why to study math? //martin-thoma.com/why-to-study-math/ Mon, 23 Jul 2012 01:14:24 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/why-to-study-math <iframe width="512" height="288" src="http://www.youtube.com/embed/aYIv4jggQJc" frameborder="0" allowfullscreen=""></iframe> <h2 id="math-is-beautiful">Math is beautiful</h2> <p>See also:</p> <ul> <li><a href="http://www.youtube.com/watch?v=I1UzGC15sBI&amp;feature=youtu.be&amp;t=3m18s">Different sizes of infinity</a></li> <li><a href="http://youtu.be/ud-GOdM255c">Beauty in Maths: math animation no.7</a> - 5D Visualization of three equations</li> </ul> <h2>Math is important</h2> <p>If you are interested in natural science, you will defenitely need math. Here are a few examples where math is directly needed:</p> <ul> <li><strong>Computer Science</strong>: All kinds of animations, stochastics is needed often, cryptography needs number theory</li> <li><strong>Physics</strong>: a lot of analysis seems to be needed, differential equations are used if processes are depend on time</li> <li><strong>Chemistry</strong>, <strong>Biology</strong>, <strong>Medicine</strong>, <strong>Psychology</strong>: again stochastics for interpreting results of experiments</li> <li><strong>economic science</strong>: modelling - I don't know anything about economic science, but I've heard they need differential equations</li> </ul> <p>Although I guess you could continue this list, but the most important reason is that it teaches you how to think logically.</p> <h2 id="jobs-are-better">Jobs are better</h2> <div style="width: 405px" class="wp-caption aligncenter"><a href="../images/2012/07/reddit-math-degree.png"><img src="../images/2012/07/reddit-math-degree.png" alt="What you earn with a math-degree ;-)" width="" height="" class="size-full wp-image-34701" /></a><p class="wp-caption-text">What you earn with a math-degree ;-)</p></div> <h2 id="math-is-worth-a-lot-of-money">Math is worth a lot of money</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/BbX44YSsQ2I" frameborder="0" allowfullscreen=""></iframe> <h2 id="math-is-fun">Math is fun</h2> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2012/07/topologist-cup.jpg"><img src="../images/2012/07/topologist-cup.jpg" alt="Only topologists really understand this joke, I guess..." width="" height="" class="size-full wp-image-34721" /></a><p class="wp-caption-text">Only topologists really understand this joke, I guess...</p></div> <div style="width: 650px" class="wp-caption aligncenter"><a href="../images/2012/07/456-top-10-signs-you-are-a-mathematician.png"><img src="../images/2012/07/456-top-10-signs-you-are-a-mathematician.png" alt="The top 10 signs you&rsquo;re a mathematician/computer scientist" width="" height="" class="size-full wp-image-34741" /></a><p class="wp-caption-text">The top 10 signs you&rsquo;re a mathematician/computer scientist</p></div> <iframe width="512" height="288" src="http://www.youtube.com/embed/mpITo-RN-bY" frameborder="0" allowfullscreen=""></iframe> <h2 id="money">Money</h2> <p>Not knowing mathematics can cost you money. An obvious example is:</p> <iframe width="512" height="384" src="//www.youtube-nocookie.com/embed/BbX44YSsQ2I" frameborder="0" allowfullscreen=""></iframe> Übersicht über Datenstrukturen //martin-thoma.com/ubersicht-uber-datenstrukturen/ Sun, 22 Jul 2012 17:38:04 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ubersicht-uber-datenstrukturen <p>Diese Übersicht beinhaltet grundlegende Datenstrukturen. Es gibt weitaus <a href="http://de.wikipedia.org/wiki/Kategorie:Datenstruktur">mehr Datenstrukturen</a> (z.B. <a href="http://de.wikipedia.org/wiki/Bloomfilter">Bloomfilter</a>), als ich hier erwähne. Diese Datenstrukturen wurden in der Vorlesung Algorithmen I bei Frau Zitterbart am KIT erklärt.</p> <h2>Array</h2> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/array.png"><img src="../images/2012/07/array.png" alt="Array" width="" height="" class="size-full wp-image-34531" /></a><p class="wp-caption-text">Array</p></div> <p>Ein Array, auch <a href="http://de.wikipedia.org/wiki/Feld_(Datentyp)">Feld</a> genannt, ist eine Datenstruktur. Charakteristika:</p> <ul> <li>Ein Array hat eine feste, nicht ver&auml;nderbare Gr&ouml;&szlig;e.</li> <li>Der Zugriff auf jedes beliebige Element erfolgt in konstanter Zeit - ist also insbesondere unabh&auml;ngig von der Gr&ouml;&szlig;e!</li> </ul> <h2>Dynamische Arrays</h2> <p>Dynamische Arrays sind wie normale Arrays, nur dass sie wachsen können. Sobald ein Element eingefügt werden soll, dass nicht mehr ins Array passen würde, allokiert man ein doppelt so großes Array und kopiert die Elemente um.</p> <p>In Java ist es ein <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Vector.html">Vector</a> bzw. eine <a href="http://docs.oracle.com/javase/7/docs/api/java/util/ArrayList.html">ArrayList</a>, in <a href="../vectors-in-cpp/" title="Vectors in C++">C++ Vektoren</a>.</p> <h2>Hashtabelle</h2> <blockquote>In der Informatik bezeichnet man eine spezielle Indexstruktur als Hashtabelle (englisch hash table oder hash map) bzw. Streuwerttabelle. Als Indexstruktur werden Hashtabellen verwendet um Datenelemente in einer gro&szlig;en Datenmenge aufzufinden. Zu Hashtabellen alternative Index-Datenstrukturen sind beispielsweise Baumstrukturen (wie etwa ein B+-Baum) und die Skip-List. Hashtabellen zeichnen sich durch einen &uuml;blicherweise konstanten Zeitaufwand bei Einf&uuml;ge- bzw. Entfernen-Operationen aus. Beim Einsatz einer Hashtabelle zur Suche in Datenmengen spricht man auch von einem Hashverfahren oder Streuspeicherverfahren.</blockquote> <p>Quelle: <a href="http://de.wikipedia.org/wiki/Hashtabelle">Hashtabelle</a></p> <p>Hashtabellen werden hier benutzt:</p> <ul> <li>Python 3.2.3: Modules/_pickle.c</li> <li>Java OpenJDK 7: <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Hashtable.html">java.util.HashTable</a> und sehr viele mehr benutzen es (Properties.java, Dictionary.java, Enum.java, ...)</li> </ul> <p>Sie garantieren eine amortisierte Laufzeit von <code>${\cal O}(1)$</code> für Suchen, Löschen und Einfügen.</p> <p>Folgende Begriffe sollte man kennen:</p> <ul> <li><a href="http://de.wikipedia.org/wiki/Divisionsrestmethode">Divisions-Rest-Methode</a>: `$h(k) = k \mod m$`</li> <li><a href="http://de.wikipedia.org/wiki/Multiplikative_Methode">Multiplikationsmethode</a>: `$h(k) = \lfloor A \cdot k \mod 1 \rfloor$`, mit z.B. `$A \approx \frac{\sqrt{5}-1}{2}$`</li> <li>offenes Hashing</li> <li><a href="http://de.wikipedia.org/wiki/Doppel-Hashing">Doppeltes Hashing</a>: `$h(k, i) = (h_1(k) + i \cdot h_2(k)) \mod m$`</li> <li><a href="http://de.wikipedia.org/wiki/Hashtabelle#Lineares_Sondieren">Lineares und quadratische Sondieren</a></li> <li>Belegungsfaktor: `$\alpha = \frac{\text{Anzahl gespeicherter Elemente}}{\text{Anzahl der Slots}}$`</li> <li>Prim&auml;re und sekund&auml;re Clusterbildung</li> </ul> <h2>Stack</h2> <div style="width: 111px" class="wp-caption alignright"><a href="../images/2012/07/stack-101x300.png"><img src="../images/2012/07/stack-101x300.png" alt="Stack a capacity of 5 elements and size of 4." width="" height="" class="size-medium wp-image-34421" /></a><p class="wp-caption-text">Stack a capacity of 5 elements and size of 4.</p></div> <p>Stacks, auch “<a href="http://de.wikipedia.org/wiki/Stapelspeicher">Stapelspeicher</a>” oder “Kellerspeicher” genannt, sind eine elementare Datenstruktur. Es sollte sie in jeder Sprache geben. In Java ist es in <a href="http://docs.oracle.com/javase/7/docs/api/java/util/Stack.html">java.util.Stack</a>, in Python sind es <a href="http://docs.python.org/tutorial/datastructures.html#using-lists-as-stacks">Listen</a> und natürlich gibt es auch in <a href="../stacks-in-cpp/" title="Stacks in C++">C++ Stacks</a>.</p> <p>Wie man am Bild sehr schön sehen kann, definiert ein Stack keine Ordnung über die Elemente. Wenn ein neues Element kommt, wird es auf den Stack gelegt. Man kann auch nur das oberste Element - in diesem Fall a - vom Stack nehmen. Deshalb werden Stacks auch als LIFO-Speicher (<em>L</em>ast <em>I</em>n <em>F</em>irst <em>O</em>ut) bezeichnet.</p> <p>Stacks werden mit dynamischen Arrays realisiert. Dazu mal ein kleines Beispiel:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.Stack</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">Stack</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">s</span> <span class="o">=</span> <span class="k">new</span> <span class="n">Stack</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">s</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">12</span><span class="o">);</span> <span class="n">s</span><span class="o">.</span><span class="na">push</span><span class="o">(</span><span class="mi">13</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="mi">100</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="n">s</span><span class="o">.</span><span class="na">push</span><span class="o">(</span><span class="n">i</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">printf</span><span class="o">(</span><span class="s">&quot;size: %d \t capacity: %d\n&quot;</span><span class="o">,</span> <span class="n">s</span><span class="o">.</span><span class="na">size</span><span class="o">(),</span> <span class="n">s</span><span class="o">.</span><span class="na">capacity</span><span class="o">());</span> <span class="o">}</span> <span class="k">while</span> <span class="o">(</span><span class="n">s</span><span class="o">.</span><span class="na">size</span><span class="o">()</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">printf</span><span class="o">(</span> <span class="s">&quot;Element: %d \t size: %d \t capacity: %d\n&quot;</span><span class="o">,</span> <span class="n">s</span><span class="o">.</span><span class="na">pop</span><span class="o">(),</span><span class="n">s</span><span class="o">.</span><span class="na">size</span><span class="o">(),</span> <span class="n">s</span><span class="o">.</span><span class="na">capacity</span><span class="o">());</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Ausgabe:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">size: <span class="m">3</span> capacity: 10 size: <span class="m">4</span> capacity: 10 size: <span class="m">5</span> capacity: 10 size: <span class="m">6</span> capacity: 10 size: <span class="m">7</span> capacity: 10 size: <span class="m">8</span> capacity: 10 size: <span class="m">9</span> capacity: 10 size: <span class="m">10</span> capacity: 10 size: <span class="m">11</span> capacity: 20 size: <span class="m">12</span> capacity: 20 size: <span class="m">13</span> capacity: 20 size: <span class="m">14</span> capacity: 20 size: <span class="m">15</span> capacity: 20 size: <span class="m">16</span> capacity: 20 size: <span class="m">17</span> capacity: 20 size: <span class="m">18</span> capacity: 20 size: <span class="m">19</span> capacity: 20 size: <span class="m">20</span> capacity: 20 size: <span class="m">21</span> capacity: 40 size: <span class="m">22</span> capacity: 40 size: <span class="m">23</span> capacity: 40 size: <span class="m">24</span> capacity: 40 size: <span class="m">25</span> capacity: 40 size: <span class="m">26</span> capacity: 40 size: <span class="m">27</span> capacity: 40 size: <span class="m">28</span> capacity: 40 size: <span class="m">29</span> capacity: 40 size: <span class="m">30</span> capacity: 40 size: <span class="m">31</span> capacity: 40 size: <span class="m">32</span> capacity: 40 size: <span class="m">33</span> capacity: 40 size: <span class="m">34</span> capacity: 40 size: <span class="m">35</span> capacity: 40 size: <span class="m">36</span> capacity: 40 size: <span class="m">37</span> capacity: 40 size: <span class="m">38</span> capacity: 40 size: <span class="m">39</span> capacity: 40 size: <span class="m">40</span> capacity: 40 size: <span class="m">41</span> capacity: 80 size: <span class="m">42</span> capacity: 80 size: <span class="m">43</span> capacity: 80 size: <span class="m">44</span> capacity: 80 size: <span class="m">45</span> capacity: 80 size: <span class="m">46</span> capacity: 80 size: <span class="m">47</span> capacity: 80 size: <span class="m">48</span> capacity: 80 size: <span class="m">49</span> capacity: 80 size: <span class="m">50</span> capacity: 80 size: <span class="m">51</span> capacity: 80 size: <span class="m">52</span> capacity: 80 size: <span class="m">53</span> capacity: 80 size: <span class="m">54</span> capacity: 80 size: <span class="m">55</span> capacity: 80 size: <span class="m">56</span> capacity: 80 size: <span class="m">57</span> capacity: 80 size: <span class="m">58</span> capacity: 80 size: <span class="m">59</span> capacity: 80 size: <span class="m">60</span> capacity: 80 size: <span class="m">61</span> capacity: 80 size: <span class="m">62</span> capacity: 80 size: <span class="m">63</span> capacity: 80 size: <span class="m">64</span> capacity: 80 size: <span class="m">65</span> capacity: 80 size: <span class="m">66</span> capacity: 80 size: <span class="m">67</span> capacity: 80 size: <span class="m">68</span> capacity: 80 size: <span class="m">69</span> capacity: 80 size: <span class="m">70</span> capacity: 80 size: <span class="m">71</span> capacity: 80 size: <span class="m">72</span> capacity: 80 size: <span class="m">73</span> capacity: 80 size: <span class="m">74</span> capacity: 80 size: <span class="m">75</span> capacity: 80 size: <span class="m">76</span> capacity: 80 size: <span class="m">77</span> capacity: 80 size: <span class="m">78</span> capacity: 80 size: <span class="m">79</span> capacity: 80 size: <span class="m">80</span> capacity: 80 size: <span class="m">81</span> capacity: 160 size: <span class="m">82</span> capacity: 160 size: <span class="m">83</span> capacity: 160 size: <span class="m">84</span> capacity: 160 size: <span class="m">85</span> capacity: 160 size: <span class="m">86</span> capacity: 160 size: <span class="m">87</span> capacity: 160 size: <span class="m">88</span> capacity: 160 size: <span class="m">89</span> capacity: 160 size: <span class="m">90</span> capacity: 160 size: <span class="m">91</span> capacity: 160 size: <span class="m">92</span> capacity: 160 size: <span class="m">93</span> capacity: 160 size: <span class="m">94</span> capacity: 160 size: <span class="m">95</span> capacity: 160 size: <span class="m">96</span> capacity: 160 size: <span class="m">97</span> capacity: 160 size: <span class="m">98</span> capacity: 160 size: <span class="m">99</span> capacity: 160 size: <span class="m">100</span> capacity: 160 size: <span class="m">101</span> capacity: 160 size: <span class="m">102</span> capacity: 160 Element: <span class="m">99</span> size: <span class="m">101</span> capacity: 160 Element: <span class="m">98</span> size: <span class="m">100</span> capacity: 160 Element: <span class="m">97</span> size: <span class="m">99</span> capacity: 160 Element: <span class="m">96</span> size: <span class="m">98</span> capacity: 160 Element: <span class="m">95</span> size: <span class="m">97</span> capacity: 160 Element: <span class="m">94</span> size: <span class="m">96</span> capacity: 160 Element: <span class="m">93</span> size: <span class="m">95</span> capacity: 160 Element: <span class="m">92</span> size: <span class="m">94</span> capacity: 160 Element: <span class="m">91</span> size: <span class="m">93</span> capacity: 160 Element: <span class="m">90</span> size: <span class="m">92</span> capacity: 160 Element: <span class="m">89</span> size: <span class="m">91</span> capacity: 160 Element: <span class="m">88</span> size: <span class="m">90</span> capacity: 160 Element: <span class="m">87</span> size: <span class="m">89</span> capacity: 160 Element: <span class="m">86</span> size: <span class="m">88</span> capacity: 160 Element: <span class="m">85</span> size: <span class="m">87</span> capacity: 160 Element: <span class="m">84</span> size: <span class="m">86</span> capacity: 160 Element: <span class="m">83</span> size: <span class="m">85</span> capacity: 160 Element: <span class="m">82</span> size: <span class="m">84</span> capacity: 160 Element: <span class="m">81</span> size: <span class="m">83</span> capacity: 160 Element: <span class="m">80</span> size: <span class="m">82</span> capacity: 160 Element: <span class="m">79</span> size: <span class="m">81</span> capacity: 160 Element: <span class="m">78</span> size: <span class="m">80</span> capacity: 160 Element: <span class="m">77</span> size: <span class="m">79</span> capacity: 160 Element: <span class="m">76</span> size: <span class="m">78</span> capacity: 160 Element: <span class="m">75</span> size: <span class="m">77</span> capacity: 160 Element: <span class="m">74</span> size: <span class="m">76</span> capacity: 160 Element: <span class="m">73</span> size: <span class="m">75</span> capacity: 160 Element: <span class="m">72</span> size: <span class="m">74</span> capacity: 160 Element: <span class="m">71</span> size: <span class="m">73</span> capacity: 160 Element: <span class="m">70</span> size: <span class="m">72</span> capacity: 160 Element: <span class="m">69</span> size: <span class="m">71</span> capacity: 160 Element: <span class="m">68</span> size: <span class="m">70</span> capacity: 160 Element: <span class="m">67</span> size: <span class="m">69</span> capacity: 160 Element: <span class="m">66</span> size: <span class="m">68</span> capacity: 160 Element: <span class="m">65</span> size: <span class="m">67</span> capacity: 160 Element: <span class="m">64</span> size: <span class="m">66</span> capacity: 160 Element: <span class="m">63</span> size: <span class="m">65</span> capacity: 160 Element: <span class="m">62</span> size: <span class="m">64</span> capacity: 160 Element: <span class="m">61</span> size: <span class="m">63</span> capacity: 160 Element: <span class="m">60</span> size: <span class="m">62</span> capacity: 160 Element: <span class="m">59</span> size: <span class="m">61</span> capacity: 160 Element: <span class="m">58</span> size: <span class="m">60</span> capacity: 160 Element: <span class="m">57</span> size: <span class="m">59</span> capacity: 160 Element: <span class="m">56</span> size: <span class="m">58</span> capacity: 160 Element: <span class="m">55</span> size: <span class="m">57</span> capacity: 160 Element: <span class="m">54</span> size: <span class="m">56</span> capacity: 160 Element: <span class="m">53</span> size: <span class="m">55</span> capacity: 160 Element: <span class="m">52</span> size: <span class="m">54</span> capacity: 160 Element: <span class="m">51</span> size: <span class="m">53</span> capacity: 160 Element: <span class="m">50</span> size: <span class="m">52</span> capacity: 160 Element: <span class="m">49</span> size: <span class="m">51</span> capacity: 160 Element: <span class="m">48</span> size: <span class="m">50</span> capacity: 160 Element: <span class="m">47</span> size: <span class="m">49</span> capacity: 160 Element: <span class="m">46</span> size: <span class="m">48</span> capacity: 160 Element: <span class="m">45</span> size: <span class="m">47</span> capacity: 160 Element: <span class="m">44</span> size: <span class="m">46</span> capacity: 160 Element: <span class="m">43</span> size: <span class="m">45</span> capacity: 160 Element: <span class="m">42</span> size: <span class="m">44</span> capacity: 160 Element: <span class="m">41</span> size: <span class="m">43</span> capacity: 160 Element: <span class="m">40</span> size: <span class="m">42</span> capacity: 160 Element: <span class="m">39</span> size: <span class="m">41</span> capacity: 160 Element: <span class="m">38</span> size: <span class="m">40</span> capacity: 160 Element: <span class="m">37</span> size: <span class="m">39</span> capacity: 160 Element: <span class="m">36</span> size: <span class="m">38</span> capacity: 160 Element: <span class="m">35</span> size: <span class="m">37</span> capacity: 160 Element: <span class="m">34</span> size: <span class="m">36</span> capacity: 160 Element: <span class="m">33</span> size: <span class="m">35</span> capacity: 160 Element: <span class="m">32</span> size: <span class="m">34</span> capacity: 160 Element: <span class="m">31</span> size: <span class="m">33</span> capacity: 160 Element: <span class="m">30</span> size: <span class="m">32</span> capacity: 160 Element: <span class="m">29</span> size: <span class="m">31</span> capacity: 160 Element: <span class="m">28</span> size: <span class="m">30</span> capacity: 160 Element: <span class="m">27</span> size: <span class="m">29</span> capacity: 160 Element: <span class="m">26</span> size: <span class="m">28</span> capacity: 160 Element: <span class="m">25</span> size: <span class="m">27</span> capacity: 160 Element: <span class="m">24</span> size: <span class="m">26</span> capacity: 160 Element: <span class="m">23</span> size: <span class="m">25</span> capacity: 160 Element: <span class="m">22</span> size: <span class="m">24</span> capacity: 160 Element: <span class="m">21</span> size: <span class="m">23</span> capacity: 160 Element: <span class="m">20</span> size: <span class="m">22</span> capacity: 160 Element: <span class="m">19</span> size: <span class="m">21</span> capacity: 160 Element: <span class="m">18</span> size: <span class="m">20</span> capacity: 160 Element: <span class="m">17</span> size: <span class="m">19</span> capacity: 160 Element: <span class="m">16</span> size: <span class="m">18</span> capacity: 160 Element: <span class="m">15</span> size: <span class="m">17</span> capacity: 160 Element: <span class="m">14</span> size: <span class="m">16</span> capacity: 160 Element: <span class="m">13</span> size: <span class="m">15</span> capacity: 160 Element: <span class="m">12</span> size: <span class="m">14</span> capacity: 160 Element: <span class="m">11</span> size: <span class="m">13</span> capacity: 160 Element: <span class="m">10</span> size: <span class="m">12</span> capacity: 160 Element: <span class="m">9</span> size: <span class="m">11</span> capacity: 160 Element: <span class="m">8</span> size: <span class="m">10</span> capacity: 160 Element: <span class="m">7</span> size: <span class="m">9</span> capacity: 160 Element: <span class="m">6</span> size: <span class="m">8</span> capacity: 160 Element: <span class="m">5</span> size: <span class="m">7</span> capacity: 160 Element: <span class="m">4</span> size: <span class="m">6</span> capacity: 160 Element: <span class="m">3</span> size: <span class="m">5</span> capacity: 160 Element: <span class="m">2</span> size: <span class="m">4</span> capacity: 160 Element: <span class="m">1</span> size: <span class="m">3</span> capacity: 160 Element: <span class="m">0</span> size: <span class="m">2</span> capacity: 160 Element: <span class="m">13</span> size: <span class="m">1</span> capacity: 160 Element: <span class="m">12</span> size: <span class="m">0</span> capacity: 160</code></pre></div> <p>Wenn man das ausführt, sieht man es recht schnell. Alternativ schaut man in die Dokumentation und liest:</p> <blockquote>The Stack class represents a last-in-first-out (LIFO) stack of objects. It extends class Vector with five operations that allow a vector to be treated as a stack.</blockquote> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Push</td> <td>`${\cal O}(1)$`</td> <td>Ein Element auf den Stack legen</td> </tr> <tr> <td>Pop</td> <td>`${\cal O}(1)$`</td> <td>Das oberste Element von der Liste nehmen</td> </tr> </table> <p>Ein Stack lässt sich als doppelt verkettete, zyklische Liste implementieren.</p> <h2>Warteschlangen</h2> <p>Warteschlangen, auch Queues genannt, sind Stacks sehr ähnlich. Beide unterstützen prinzipiell nur zwei Operationen. Bei Stacks nanne es sich PUSH und POP, bei Warteschlangen heißt es ENQUEUE und DEQUEUE. Im Unterschied zum Stack wird bei der Warteschlange das Element nicht von oben wieder weggenommen, sondern von hinten. Das Bild einer Warteschlange ist hier sehr passend.</p> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Enqueue</td> <td>`${\cal O}(1)$`</td> <td>Ein Element auf den Stack legen</td> </tr> <tr> <td>Dequeue</td> <td>`${\cal O}(1)$`</td> <td>Das oberste Element von der Liste nehmen</td> </tr> </table> <p>Eine Warteschlange lässt sich als doppelt verkettete, zyklische Liste implementieren.</p> <h2>Verkettete Listen</h2> <p>Wie bei allen Datenstrukturen, kann man für verkettete Listen mehr Operationen definieren und umsetzen, als ich hier aufliste. Eine gute Menge von Operationen wird durch das <a href="http://docs.oracle.com/javase/7/docs/api/java/util/List.html">Java List Interface</a> vorgegeben.</p> <h3>Einfach verkettete Liste</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/singly-linked-list.png"><img src="../images/2012/07/singly-linked-list.png" alt="Singly linked list" width="" height="" class="size-full wp-image-34051" /></a><p class="wp-caption-text">Singly linked list</p></div> <p>Sei <code>$n$</code> die Anzahl der Elemente der Liste.</p> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Suchen</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Element ist am Ende der Liste</td> </tr> <tr> <td>Minimum</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Element ist am Ende der Liste</td> </tr> <tr> <td>Maximum</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Element ist am Ende der Liste</td> </tr> <tr> <td>Einf&uuml;gen am Anfang</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> <tr> <td>Wahlfreies Einf&uuml;gen</td> <td>`${\cal O}(n)$`</td> <td></td> </tr> <tr> <td>L&ouml;schen</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Suchen</td> </tr> <tr> <td>Vorg&auml;nger</td> <td>`${\cal O}(n)$`</td> <td></td> </tr> <tr> <td>Nachfolger</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> </table> <h3>Doppelt verkettete Liste</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/doubly-linked-list.png"><img src="../images/2012/07/doubly-linked-list.png" alt="Doubly linked list" width="" height="" class="size-full wp-image-34031" /></a><p class="wp-caption-text">Doubly linked list</p></div> <p>Sei <code>$n$</code> die Anzahl der Elemente der Liste.</p> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Suchen</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Element ist am Ende der Liste</td> </tr> <tr> <td>Minimum</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Element ist am Ende der Liste</td> </tr> <tr> <td>Maximum</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Element ist am Ende der Liste</td> </tr> <tr> <td>Einf&uuml;gen am Anfang</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> <tr> <td>Wahlfreies Einf&uuml;gen</td> <td>`${\cal O}(n)$`</td> <td></td> </tr> <tr> <td>L&ouml;schen</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Suchen</td> </tr> <tr> <td>Vorg&auml;nger</td> <td>`${\cal O}(1)$`</td> <td>Nur hier ist die doppelt-verkettete Liste besser als die einfach verkettete Liste.</td> </tr> <tr> <td>Nachfolger</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> </table> <h2>B&auml;ume</h2> <p>In der Vorlesung wurden Bäume sehr unpräzise eingeführt. Ich versuche das mal etwas präziser zu machen:</p> <div class="definition">Sei `$G = (V, E)$` ein gerichteter Graph. `$G$` hei&szlig;t <strong>gerichteter Baum</strong> `$: \Leftrightarrow \exists_{r \in V} \forall_{x \in V}:$`Es exisitert genau ein Pfad von `$r$` nach `$x$`.</div> <div class="definition">Sei `$G = (V, E)$` ein gerichteter Baum und sei `$r \in V$` das `$r$` aus der Definition. `$r$` hei&szlig;t <strong>Wurzel</strong> von `$G$`.</div> <p>ACHTUNG: Die folgende Definition habe ich mir ausgedacht! NICHT IN DER KLAUSUR VERWENDEN!</p> <div class="definition">Sei `$E \subseteq V \times V$` eine Menge ungerichteter Kanten. Dann bezeichne `$G(E) := \{(v, w) | \{v, w\} \in E\}$` die Menge aller zugeh&ouml;rigen gerichteten Kanten.</div> <div class="definition">Sei `$U = (V, E)$` ein ungerichteter Graph. `$U$` hei&szlig;t ein <strong>ungerichteter Baum</strong> `$:\Leftrightarrow \exists$` gerichteten Baum `$G = (V, E')$` mit `$E' \subsetneq G(E)$`.</div> <div class="definition">Sei `$G = (V, E)$` ein Baum und `$x, y \in V$`. `$x$` hei&szlig;t <strong>Elternknoten</strong> von `$y :\Leftrightarrow x$` liegt auf dem Pfad von der Wurzel nach `$y$` direkt vor `$y$`.</div> <div class="definition">Sei `$G = (V, E)$` ein Baum und `$x, y \in V$`. `$x$` hei&szlig;t <strong>Kindknoten</strong> von `$y :\Leftrightarrow y$` ist Elternknoten von `$x$`.</div> <h3>Bin&auml;re B&auml;ume</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/binary-tree.png"><img src="../images/2012/07/binary-tree.png" alt="Binary tree datastructure" width="" height="" class="size-full wp-image-33851" /></a><p class="wp-caption-text">Binary tree datastructure</p></div> <div class="definition">Sei `$G = (V, E)$` ein Baum. `$G$` hei&szlig;t <strong>bin&auml;rer Baum</strong> `$:\Leftrightarrow \forall_{x \in V}: x$` hat h&ouml;chstens zwei Kindknoten.</div> <p>Ich beziehe mich im folgenden auf ungerichtete, binäre Bäume. Soll heißen, jeder Knoten kennt seine Kinder- <strong>und</strong> seinen Vaterknoten.</p> <p>Wie würde man das implementieren? Im Prinzip wie eine doppelt verkettete Liste. Jeder Knoten hat einen Zeiger auf den Eltern-Knoten und zwei Zeiger auf die Kindknoten.</p> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Suchen</td> <td>`${\cal O}(|V| + |E|)$`</td> <td>&rarr; <a href="http://de.wikipedia.org/wiki/Traversierung#Graphentheorie">Graphentraversierung</a></td> </tr> <tr> <td>Minimum</td> <td>`${\cal O}(|V| + |E|)$`</td> <td>&rarr; <a href="http://de.wikipedia.org/wiki/Traversierung#Graphentheorie">Graphentraversierung</a></td> </tr> <tr> <td>Maximum</td> <td>`${\cal O}(|V| + |E|)$`</td> <td>&rarr; <a href="http://de.wikipedia.org/wiki/Traversierung#Graphentheorie">Graphentraversierung</a></td> </tr> <tr> <td>Einf&uuml;gen</td> <td>`${\cal O}(|V|)$`</td> <td></td> </tr> <tr> <td>L&ouml;schen</td> <td>`${\cal O}(|V| + |E|)$`</td> <td>&rarr; Suchen</td> </tr> <tr> <td>Vorg&auml;nger</td> <td>`${\cal O}(1)$`</td> <td>Implementierungsabh&auml;ngig!</td> </tr> <tr> <td>Nachfolger</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> </table> <h3>Suchb&auml;ume</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/binary-search-tree.png"><img src="../images/2012/07/binary-search-tree.png" alt="Binary search tree" width="" height="" class="size-full wp-image-33871" /></a><p class="wp-caption-text">Binary search tree</p></div> <p>Dieser Baum hat die gleichen Werte wie der Baum oberhalb, aber es gilt nun: Der Wert aller Knoten links vom aktuellen Konten ist kleiner oder gleich dem des aktuelle, der Wert aller Knoten rechts davon ist echt größer.</p> <p>Ich beschränke mich hier auf binäre Suchbäume.</p> <p>Damit ergeben sich folgende Laufzeiten: Sei <code>$G = (V, E)$</code> ein beliebiger binärer Suchbaum. Jeder Knoten kennt seine Kinder- <strong>und</strong> seinen Vaterknoten.</p> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Suchen</td> <td>`${\cal O}(|V|)$`</td> <td>&rarr; Verkettete Liste</td> </tr> <tr> <td>Minimum</td> <td>`${\cal O}(|V|)$`</td> <td>&rarr; Verkettete Liste</td> </tr> <tr> <td>Maximum</td> <td>`${\cal O}(|V|)$`</td> <td>&rarr; Verkettete Liste</td> </tr> <tr> <td>Einf&uuml;gen</td> <td>`${\cal O}(|V|)$`</td> <td>&rarr; Verkettete Liste</td> </tr> <tr> <td>L&ouml;schen</td> <td>`${\cal O}(|V|)$`</td> <td>&rarr; Verkettete Liste</td> </tr> <tr> <td>Vorg&auml;nger</td> <td>`${\cal O}(1)$`</td> <td>Implementierungsabh&auml;ngig!</td> </tr> <tr> <td>Nachfolger</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> </table> <h4>Rot-Schwarz-B&auml;ume</h4> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/red-black-tree1.png"><img src="../images/2012/07/red-black-tree1.png" alt="Red Black Tree" width="" height="" class="size-full wp-image-34071" /></a><p class="wp-caption-text">Red Black Tree</p></div> <p>Sei <code>$G = (V, E)$</code> ein binärer Suchbaum. G heißt Rot-Schwarz-Baum <code>$: \Leftrightarrow$</code> Für G gilt:</p> <ol> <li>Jeder Knoten ist entweder Rot oder Schwarz.</li> <li>Der Wurzelknoten ist schwarz.</li> <li>Die Blattknoten sind schwarz.</li> <li>Ein Knoten ist rot `$\Rightarrow$` Beide Kinder sind schwarz.</li> <li>`$\forall x \in V:$` Alle Pfade von x zu einem Blatt haben die gleiche Anzahl schwarzer Knoten.</li> </ol> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Suchen</td> <td>`${\cal O}(\lg n)$`</td> <td></td> </tr> <tr> <td>Minimum</td> <td>`${\cal O}(\lg n)$`</td> <td></td> </tr> <tr> <td>Maximum</td> <td>`${\cal O}(\lg n)$`</td> <td></td> </tr> <tr> <td>Einf&uuml;gen</td> <td>`${\cal O}(\lg n)$`</td> <td></td> </tr> <tr> <td>L&ouml;schen</td> <td>`${\cal O}(\lg n)$`</td> <td></td> </tr> <tr> <td>Vorg&auml;nger</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> <tr> <td>Nachfolger</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> </table> <p>Eine Python-Implementation ist hier zu finden: <a href="https://github.com/MartinThoma/algorithms/blob/master/datastructures/redBlackTree.py">https://github.com/MartinThoma/algorithms</a></p> <h3>Heaps</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/heap.png"><img src="../images/2012/07/heap.png" alt="Ein bin&auml;rer Min-Heap" width="" height="" class="size-full wp-image-34361" /></a><p class="wp-caption-text">Ein bin&auml;rer Min-Heap</p></div> <p>Ich beschränke mich im folgenden auf <a href="http://de.wikipedia.org/wiki/Bin%C3%A4rer_Heap">binäre Min-Heaps</a>.</p> <table> <tr> <th>Operation</th> <th>Worst-Case-Laufzeit</th> <th>Anmerkungen</th> </tr> <tr> <td>Suchen</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Falls als array dargestellt, einfach alle Elemente des Arrays durchlaufen</td> </tr> <tr style="background-color:#99FF99"> <td>Minimum</td> <td>`${\cal O}(1)$`</td> <td></td> </tr> <tr style="background-color:#99FF99"> <td>Extract-Minimum</td> <td>`${\cal O}(\log n)$`</td> <td>&rarr; Heapify</td> </tr> <tr> <td>Maximum</td> <td>`${\cal O}(n)$`</td> <td>&rarr; Suche</td> </tr> <tr> <td>Einf&uuml;gen</td> <td>`${\cal O}(\log n)$`</td> <td>&rarr; Heapify</td> </tr> <tr> <td>L&ouml;schen</td> <td>`${\cal O}(\log n)$`</td> <td>&rarr; Heapify (bei bekannter Position des Elements, sonst siehe Suche)</td> </tr> <tr> <td>Vorg&auml;nger</td> <td>`${\cal O}(1)$`</td> <td>Hat keine besondere Bedeutung in Heaps.</td> </tr> <tr> <td>Nachfolger</td> <td>`${\cal O} (1)$`</td> <td>Hat keine besondere Bedeutung in Heaps.</td> </tr> </table> <h3>B-B&auml;ume</h3> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-2.png"><img src="../images/2012/07/b-tree-2.png" alt="B-Baum der Ordnung 2" width="" height="" class="size-full wp-image-34581" /></a><p class="wp-caption-text">B-Baum der Ordnung 2</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/07/b-tree-3.png"><img src="../images/2012/07/b-tree-3.png" alt="B-Baum der Ordnung 3" width="" height="" class="size-full wp-image-34591" /></a><p class="wp-caption-text">B-Baum der Ordnung 3</p></div> <blockquote>Ein B-Baum ist ein immer vollst&auml;ndig balancierter Baum, der Daten sortiert nach Schl&uuml;sseln speichert. Er kann bin&auml;r sein, ist aber im Allgemeinen kein Bin&auml;rbaum. Das Einf&uuml;gen, Suchen und L&ouml;schen von Daten in B-B&auml;umen ist in amortisiert logarithmischer Zeit m&ouml;glich. B-B&auml;ume wachsen &ndash; und schrumpfen &ndash; anders als viele Suchb&auml;ume von den Bl&auml;ttern hin zur Wurzel.</blockquote> <p>Quelle: <a href="http://de.wikipedia.org/wiki/B-Baum">Wikipedia</a></p> <p>Die beiden abgebildeten B-Bäume sind entstanden, indem die Zahlen von 0 bis 19 in aufsteigener Reihenfolge eingefügt wurden.</p> <p>Für einen B-Baum der Ordnung t, <code>$t \geq 2$</code>, gilt:</p> <ul> <li>Alle Pfade von der Wurzel zu einem Blatt sind gleich lang.</li> <li>Die Wurzel hat mindestens 2, h&ouml;chstens 2t Kinder.</li> <li>Alle anderen inneren Knoten haben mindestens t, h&ouml;chstens 2t Kinder.</li> <li>Jeder Knoten mit i Kindern hat i-1 Schl&uuml;ssel.</li> </ul> <p>Die beiden B-Bäume habe ich mit <a href="https://gist.github.com/3159687">diesem Script</a> erstellt.</p> <p>Mehr zu B-Bäumen gibt es in diesem <a href="../b-baume/" title="B-B&auml;ume">Artikel über B-Bäume</a>.</p> <h3>Tries</h3> <div style="width: 210px" class="wp-caption aligncenter"><a href="../images/2012/07/trie.png"><img src="../images/2012/07/trie.png" alt="Trie" width="" height="" class="size-full wp-image-34621" /></a><p class="wp-caption-text">Trie</p></div> <p>Bildquelle: <a href="http://commons.wikimedia.org/wiki/File:Trie.svg">Wikipedia</a></p> <p>Ein Trie ist ein spezieller digitaler Baum.</p> <blockquote>Ein Trie oder Pr&auml;fixbaum ist eine Datenstruktur, die in der Informatik zum Suchen nach Zeichenketten verwendet wird. Es handelt sich dabei um einen speziellen Suchbaum zur gleichzeitigen Speicherung mehrerer Zeichenketten.</blockquote> <p>Quelle: <a href="http://de.wikipedia.org/wiki/Trie">Wikipedia</a></p> <p>Wo werden Tries genutzt?</p> <ul> <li>Python charmap encoder (<a href="http://mail.python.org/pipermail/patches/2006-May/019891.html">source</a>)</li> <li>Der <a href="http://docs.oracle.com/javase/7/docs/api/java/text/Normalizer.html">Normalizer</a> scheint Tries zu verwenden.</li> </ul> Swing II: How to arrange Objects //martin-thoma.com/swing-ii-how-to-arrange-objects/ Sat, 21 Jul 2012 17:00:44 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/swing-ii-how-to-arrange-objects <h2>Without GUI</h2> <p>Objects can be arranged with <a href="http://docs.oracle.com/javase/7/docs/api/java/awt/GridBagLayout.html">GridBagLayout</a> and <a href="http://docs.oracle.com/javase/7/docs/api/java/awt/GridBagConstraints.html">GridBagConstraints</a>. This is an example: <img src="../images/2012/07/java-swing-grid-bag.png" alt="GridBag example (Java Swing)" title="GridBag example (Java Swing)" width="198" height="199" class="size-full wp-image-33451" /></p> <p>Code:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.awt.GridBagConstraints</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.awt.GridBagLayout</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.awt.Insets</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.awt.MouseInfo</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.awt.Point</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JButton</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JFrame</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JPanel</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JTextField</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="c1">// Open the window where the mouse pointer is</span> <span class="n">Point</span> <span class="n">location</span> <span class="o">=</span> <span class="n">MouseInfo</span><span class="o">.</span><span class="na">getPointerInfo</span><span class="o">().</span><span class="na">getLocation</span><span class="o">();</span> <span class="kt">int</span> <span class="n">x</span> <span class="o">=</span> <span class="o">(</span><span class="kt">int</span><span class="o">)</span> <span class="n">location</span><span class="o">.</span><span class="na">getX</span><span class="o">();</span> <span class="kt">int</span> <span class="n">y</span> <span class="o">=</span> <span class="o">(</span><span class="kt">int</span><span class="o">)</span> <span class="n">location</span><span class="o">.</span><span class="na">getY</span><span class="o">();</span> <span class="n">JFrame</span> <span class="n">frame</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JFrame</span><span class="o">(</span><span class="s">&quot;My title!&quot;</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setLocation</span><span class="o">(</span><span class="n">x</span><span class="o">,</span> <span class="n">y</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setVisible</span><span class="o">(</span><span class="kc">true</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setSize</span><span class="o">(</span><span class="mi">200</span><span class="o">,</span> <span class="mi">200</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setDefaultCloseOperation</span><span class="o">(</span><span class="n">JFrame</span><span class="o">.</span><span class="na">EXIT_ON_CLOSE</span><span class="o">);</span> <span class="n">JPanel</span> <span class="n">panel</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JPanel</span><span class="o">(</span><span class="k">new</span> <span class="nf">GridBagLayout</span><span class="o">());</span> <span class="n">frame</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">panel</span><span class="o">);</span> <span class="c1">//set the size of the window to the maximum</span> <span class="c1">//frame.setExtendedState(frame.getExtendedState() |</span> <span class="c1">// Frame.MAXIMIZED_BOTH);</span> <span class="n">JButton</span> <span class="n">button1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;1&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;2&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button3</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;3&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button4</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;4&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button5</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;5&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button6</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;6&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button7</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;7&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button8</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;8&quot;</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button9</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;9&quot;</span><span class="o">);</span> <span class="n">Insets</span> <span class="n">i</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Insets</span><span class="o">(</span><span class="mi">5</span><span class="o">,</span> <span class="mi">5</span><span class="o">,</span> <span class="mi">5</span><span class="o">,</span> <span class="mi">5</span><span class="o">);</span> <span class="n">JTextField</span> <span class="n">tf</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JTextField</span><span class="o">(</span><span class="mi">13</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">cText</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">cText</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">cText</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">cText</span><span class="o">.</span><span class="na">gridwidth</span> <span class="o">=</span> <span class="n">GridBagConstraints</span><span class="o">.</span><span class="na">REMAINDER</span><span class="o">;</span> <span class="n">cText</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">tf</span><span class="o">,</span><span class="n">cText</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c1</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c1</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">c1</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">c1</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button1</span><span class="o">,</span> <span class="n">c1</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c2</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">c2</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">c2</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button2</span><span class="o">,</span> <span class="n">c2</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c3</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c3</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">c3</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">c3</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button3</span><span class="o">,</span> <span class="n">c3</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c4</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c4</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">c4</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">c4</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button4</span><span class="o">,</span> <span class="n">c4</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c5</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c5</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">c5</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">c5</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button5</span><span class="o">,</span> <span class="n">c5</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c6</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c6</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">c6</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">c6</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button6</span><span class="o">,</span> <span class="n">c6</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c7</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c7</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">c7</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">3</span><span class="o">;</span> <span class="n">c7</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button7</span><span class="o">,</span> <span class="n">c7</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c8</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c8</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">c8</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">3</span><span class="o">;</span> <span class="n">c8</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button8</span><span class="o">,</span> <span class="n">c8</span><span class="o">);</span> <span class="n">GridBagConstraints</span> <span class="n">c9</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">GridBagConstraints</span><span class="o">();</span> <span class="n">c9</span><span class="o">.</span><span class="na">gridx</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">c9</span><span class="o">.</span><span class="na">gridy</span> <span class="o">=</span> <span class="mi">3</span><span class="o">;</span> <span class="n">c9</span><span class="o">.</span><span class="na">insets</span> <span class="o">=</span> <span class="n">i</span><span class="o">;</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button9</span><span class="o">,</span> <span class="n">c9</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>Google WindowBuilder</h2> <p>Goole offers a free Eclipse plugin called <a href="https://developers.google.com/java-dev-tools/wbpro/">WindowBuilder</a>:</p> <blockquote>WindowBuilder is a powerful and easy to use bi-directional Java GUI designer that makes it very easy to create Java GUI applications without spending a lot of time writing code to display simple forms.</blockquote> <h3>Installation</h3> <p>They offer great <a href="https://developers.google.com/java-dev-tools/wbpro/installation/">installation instructions</a>!</p> <p>(The download takes a while. Time to make a cup of tea.)</p> <h3>Editing</h3> <p>You have to open your project with the window builder:</p> <div style="width: 295px" class="wp-caption aligncenter"><a href="../images/2012/07/eclipse-open-with-window-builder-285x300.png"><img src="../images/2012/07/eclipse-open-with-window-builder-285x300.png" alt="Open existing SWING-file with Window Builder" width="" height="" class="size-medium wp-image-33501" /></a><p class="wp-caption-text">Open existing SWING-file with Window Builder</p></div> <p>The Window-Builder-View looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/eclipse-window-builder-300x157.png"><img src="../images/2012/07/eclipse-window-builder-300x157.png" alt="Eclipse WindowBuilder View" width="" height="" class="size-medium wp-image-33541" /></a><p class="wp-caption-text">Eclipse WindowBuilder View</p></div> <p>You can easily resize the window:</p> <div style="width: 268px" class="wp-caption aligncenter"><a href="../images/2012/07/eclipse-window-builder-resize-258x300.png"><img src="../images/2012/07/eclipse-window-builder-resize-258x300.png" alt="Resize a window with WindowBuilder" width="" height="" class="size-medium wp-image-33521" /></a><p class="wp-caption-text">Resize a window with WindowBuilder</p></div> <p>Positioning single components is also simple:</p> <div style="width: 259px" class="wp-caption aligncenter"><a href="../images/2012/07/eclipse-window-builder-component.png"><img src="../images/2012/07/eclipse-window-builder-component.png" alt="Position a single component with WindowBuilder" width="" height="" class="size-full wp-image-33531" /></a><p class="wp-caption-text">Position a single component with WindowBuilder</p></div> <p>Adding a menu bar worked fine:</p> <div style="width: 237px" class="wp-caption aligncenter"><a href="../images/2012/07/eclipse-window-builder-menu.png"><img src="../images/2012/07/eclipse-window-builder-menu.png" alt="MenuBar added with WindowBuilder" width="" height="" class="size-full wp-image-33561" /></a><p class="wp-caption-text">MenuBar added with WindowBuilder</p></div> <h2>See also</h2> <ul> <li><a href="http://docs.oracle.com/javase/tutorial/uiswing/layout/gridbag.html">How to Use GridBagLayout</a></li> <li><a href="http://stackoverflow.com/q/1832432/562769">Which Swing layout(s) do you recommend?</a></li> </ul> Swing I: How to use Swing //martin-thoma.com/how-to-use-swing/ Fri, 20 Jul 2012 17:00:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-use-swing <p><a href="http://en.wikipedia.org/wiki/Swing_(Java)">Swing</a> is a Java package for creating graphical user interfaces (GUI). I will give you complete, runnable examples how you could use Swing. All examples are done in <code>test.java</code></p> <h2>Basic examples</h2> <h3>JFrame</h3> <p>The basic class is <a href="http://docs.oracle.com/javase/7/docs/api/javax/swing/JFrame.html">JFrame</a>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">javax.swing.JFrame</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">JFrame</span> <span class="n">frame</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JFrame</span><span class="o">(</span><span class="s">&quot;My title!&quot;</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setVisible</span><span class="o">(</span><span class="kc">true</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setSize</span><span class="o">(</span><span class="mi">200</span><span class="o">,</span> <span class="mi">200</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setDefaultCloseOperation</span><span class="o">(</span><span class="n">JFrame</span><span class="o">.</span><span class="na">EXIT_ON_CLOSE</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>You will get: <a href="../images/2012/07/java-swing-JFrame.png"><img src="../images/2012/07/java-swing-JFrame.png" alt="Java Swing: JFrame" title="Java Swing: JFrame" width="300" height="201" class="size-full wp-image-33311" /></a></p> <h3>JPanel</h3> <p>You add your elements to a JPanel:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">javax.swing.JButton</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JFrame</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JLabel</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JPanel</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">JFrame</span> <span class="n">frame</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JFrame</span><span class="o">(</span><span class="s">&quot;My title!&quot;</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setVisible</span><span class="o">(</span><span class="kc">true</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setSize</span><span class="o">(</span><span class="mi">300</span><span class="o">,</span> <span class="mi">150</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setDefaultCloseOperation</span><span class="o">(</span><span class="n">JFrame</span><span class="o">.</span><span class="na">EXIT_ON_CLOSE</span><span class="o">);</span> <span class="n">JPanel</span> <span class="n">panel</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JPanel</span><span class="o">();</span> <span class="n">frame</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">panel</span><span class="o">);</span> <span class="n">JLabel</span> <span class="n">label</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JLabel</span><span class="o">(</span><span class="s">&quot;my label&quot;</span><span class="o">);</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">label</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;my button&quot;</span><span class="o">);</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>It looks like this: <a href="../images/2012/07/java-swing-jpanel.png"><img src="../images/2012/07/java-swing-jpanel.png" alt="Java Swing: JPanel, JLabel and JButton" title="Java Swing: JPanel, JLabel and JButton" width="300" height="151" class="size-full wp-image-33341" /></a></p> <h2>Action Listeners</h2> <p>This is the most simple example of an <a href="http://docs.oracle.com/javase/7/docs/api/java/awt/event/ActionListener.html">ActionListener</a>. When you click on the button, it creates a new JFrame.</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.awt.event.ActionEvent</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.awt.event.ActionListener</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JButton</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JFrame</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JLabel</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">javax.swing.JPanel</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">JFrame</span> <span class="n">frame</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JFrame</span><span class="o">(</span><span class="s">&quot;My title!&quot;</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setVisible</span><span class="o">(</span><span class="kc">true</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setSize</span><span class="o">(</span><span class="mi">300</span><span class="o">,</span> <span class="mi">150</span><span class="o">);</span> <span class="n">frame</span><span class="o">.</span><span class="na">setDefaultCloseOperation</span><span class="o">(</span><span class="n">JFrame</span><span class="o">.</span><span class="na">EXIT_ON_CLOSE</span><span class="o">);</span> <span class="n">JPanel</span> <span class="n">panel</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JPanel</span><span class="o">();</span> <span class="n">frame</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">panel</span><span class="o">);</span> <span class="n">JLabel</span> <span class="n">label</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JLabel</span><span class="o">(</span><span class="s">&quot;my label&quot;</span><span class="o">);</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">label</span><span class="o">);</span> <span class="n">JButton</span> <span class="n">button</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JButton</span><span class="o">(</span><span class="s">&quot;my button&quot;</span><span class="o">);</span> <span class="n">panel</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">button</span><span class="o">);</span> <span class="n">button</span><span class="o">.</span><span class="na">addActionListener</span><span class="o">(</span><span class="k">new</span> <span class="nf">MyAction</span><span class="o">());</span> <span class="o">}</span> <span class="kd">static</span> <span class="kd">class</span> <span class="nc">MyAction</span> <span class="kd">implements</span> <span class="n">ActionListener</span> <span class="o">{</span> <span class="nd">@Override</span> <span class="kd">public</span> <span class="kt">void</span> <span class="nf">actionPerformed</span><span class="o">(</span><span class="n">ActionEvent</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">JFrame</span> <span class="n">frame2</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">JFrame</span><span class="o">(</span><span class="s">&quot;clicked&quot;</span><span class="o">);</span> <span class="n">frame2</span><span class="o">.</span><span class="na">setVisible</span><span class="o">(</span><span class="kc">true</span><span class="o">);</span> <span class="n">frame2</span><span class="o">.</span><span class="na">setSize</span><span class="o">(</span><span class="mi">200</span><span class="o">,</span><span class="mi">200</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <h2>See also</h2> <ul> <li><a href="http://docs.oracle.com/javase/7/docs/api/javax/swing/package-summary.html">Java 7 Swing Documentation</a></li> <li><a href="http://docs.oracle.com/javase/tutorial/uiswing/">Trail: Creating a GUI With JFC/Swing</a></li> </ul> <div class="info">Continue with part II: <a href="../swing-ii-how-to-arrange-objects/">How to arrange Objects with Swing</a></div> How to parse command line arguments in Java //martin-thoma.com/how-to-parse-command-line-arguments-in-java/ Thu, 19 Jul 2012 17:00:04 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-parse-command-line-arguments-in-java <p>If you are using Eclipse, you might want to add your arguments. To specify them, go to: Run → Run Configurations … → Arguments</p> <h2>args4j</h2> <blockquote>args4j is a small Java class library that makes it easy to parse command line options/arguments in your CUI application.</blockquote> <p>Source: <a href="http://args4j.kohsuke.org/">args4j.kohsuke.org</a></p> <p>Lets see how easy it really is.</p> <h3>Requirements</h3> <p>First, you have to get the package. It is not in my Ubuntu-Version, but <a href="http://packages.ubuntu.com/quantal/libargs4j-java">Ubuntu Quantal will have args4j</a>. The package is called <code>libargs4j-java</code>.</p> <p>If you can’t install it this way, you have to <a href="http://maven.jenkins-ci.org/content/repositories/releases/args4j/">download args4j</a>. Currently, it is <a href="http://maven.jenkins-ci.org/content/repositories/releases/args4j/args4j/2.0.21/args4j-2.0.21.jar">args4j-2.0.21.jar</a>.</p> <p>You can add this as an external jar to Eclipse:</p> <ol> <li>Right-click on your project.</li> <li>Select "Properties"</li> <li>Type "java build path" in the input field at the upper left corner of the window.</li> </ol> <p>Now it should look like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/java-eclipse-project-properties-libraries-300x214.png"><img src="../images/2012/07/java-eclipse-project-properties-libraries-300x214.png" alt="Project properties in Eclipse - Libraries" width="" height="" class="size-medium wp-image-33151" /></a><p class="wp-caption-text">Project properties in Eclipse - Libraries</p></div> <p>Now you have to click on “Add External Jar” and add the args4j.jar file.</p> <h3>Source Example</h3> <p>As always in Java, you add another class for parsing your command line values. I’ve called it CommandLineValues.java and it does only check for the command line argument <code>-i FILE</code> or <code>--input FILE</code>.</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.io.File</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">org.kohsuke.args4j.CmdLineException</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">org.kohsuke.args4j.CmdLineParser</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">org.kohsuke.args4j.Option</span><span class="o">;</span> <span class="cm">/**</span> <span class="cm"> * This class handles the programs arguments.</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">CommandLineValues</span> <span class="o">{</span> <span class="nd">@Option</span><span class="o">(</span><span class="n">name</span> <span class="o">=</span> <span class="s">&quot;-i&quot;</span><span class="o">,</span> <span class="n">aliases</span> <span class="o">=</span> <span class="o">{</span> <span class="s">&quot;--input&quot;</span> <span class="o">},</span> <span class="n">required</span> <span class="o">=</span> <span class="kc">true</span><span class="o">,</span> <span class="n">usage</span> <span class="o">=</span> <span class="s">&quot;input file with two matrices&quot;</span><span class="o">)</span> <span class="kd">private</span> <span class="n">File</span> <span class="n">source</span><span class="o">;</span> <span class="kd">private</span> <span class="kt">boolean</span> <span class="n">errorFree</span> <span class="o">=</span> <span class="kc">false</span><span class="o">;</span> <span class="kd">public</span> <span class="nf">CommandLineValues</span><span class="o">(</span><span class="n">String</span><span class="o">...</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">CmdLineParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">CmdLineParser</span><span class="o">(</span><span class="k">this</span><span class="o">);</span> <span class="n">parser</span><span class="o">.</span><span class="na">setUsageWidth</span><span class="o">(</span><span class="mi">80</span><span class="o">);</span> <span class="k">try</span> <span class="o">{</span> <span class="n">parser</span><span class="o">.</span><span class="na">parseArgument</span><span class="o">(</span><span class="n">args</span><span class="o">);</span> <span class="k">if</span> <span class="o">(!</span><span class="n">getSource</span><span class="o">().</span><span class="na">isFile</span><span class="o">())</span> <span class="o">{</span> <span class="k">throw</span> <span class="k">new</span> <span class="nf">CmdLineException</span><span class="o">(</span><span class="n">parser</span><span class="o">,</span> <span class="s">&quot;--input is no valid input file.&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="n">errorFree</span> <span class="o">=</span> <span class="kc">true</span><span class="o">;</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">CmdLineException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">e</span><span class="o">.</span><span class="na">getMessage</span><span class="o">());</span> <span class="n">parser</span><span class="o">.</span><span class="na">printUsage</span><span class="o">(</span><span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Returns whether the parameters could be parsed without an</span> <span class="cm"> * error.</span> <span class="cm"> *</span> <span class="cm"> * @return true if no error occurred.</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="kt">boolean</span> <span class="nf">isErrorFree</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">errorFree</span><span class="o">;</span> <span class="o">}</span> <span class="cm">/**</span> <span class="cm"> * Returns the source file.</span> <span class="cm"> *</span> <span class="cm"> * @return The source file.</span> <span class="cm"> */</span> <span class="kd">public</span> <span class="n">File</span> <span class="nf">getSource</span><span class="o">()</span> <span class="o">{</span> <span class="k">return</span> <span class="n">source</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Here is some part of the main file:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">CommandLineValues</span> <span class="n">values</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">CommandLineValues</span><span class="o">(</span><span class="n">args</span><span class="o">);</span> <span class="n">CmdLineParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">CmdLineParser</span><span class="o">(</span><span class="n">values</span><span class="o">);</span> <span class="k">try</span> <span class="o">{</span> <span class="n">parser</span><span class="o">.</span><span class="na">parseArgument</span><span class="o">(</span><span class="n">args</span><span class="o">);</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">CmdLineException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">exit</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="o">}</span> <span class="c1">// Now you can use the command line values</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="n">matrices</span> <span class="o">=</span> <span class="n">read</span><span class="o">(</span><span class="n">values</span><span class="o">.</span><span class="na">getSource</span><span class="o">());</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="n">ijkAlgorithm</span><span class="o">(</span><span class="n">A</span><span class="o">,</span> <span class="n">B</span><span class="o">);</span> <span class="n">printMatrix</span><span class="o">(</span><span class="n">C</span><span class="o">);</span> <span class="o">}</span></code></pre></div> <h3>Usage Examples</h3> <p>If you do not specify the required parameters, you get a quite good error message:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~/Desktop<span class="sb">`</span><span class="nv">$ </span>java -jar matrix-multiplication.jar Option <span class="s2">&quot;-i (--input)&quot;</span> is required -i <span class="o">(</span>--input<span class="o">)</span> FILE : input file with two matrices</code></pre></div> <p>Help is <strong>not</strong> automatically generated:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~/Desktop<span class="nv">$`</span> java -jar matrix-multiplication.jar --help <span class="s2">&quot;--help&quot;</span> is not a valid option -i <span class="o">(</span>--input<span class="o">)</span> FILE : input file with two matrices</code></pre></div> <p>If you want to have default parameters, you simply assign the values to the attributes:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="nd">@Option</span><span class="o">(</span><span class="n">name</span> <span class="o">=</span> <span class="s">&quot;-l&quot;</span><span class="o">,</span> <span class="n">aliases</span> <span class="o">=</span> <span class="o">{</span> <span class="s">&quot;--leafsize&quot;</span> <span class="o">},</span> <span class="n">required</span> <span class="o">=</span> <span class="kc">false</span><span class="o">,</span> <span class="n">usage</span> <span class="o">=</span> <span class="s">&quot;input file with two matrices&quot;</span><span class="o">)</span> <span class="kd">private</span> <span class="kt">int</span> <span class="n">leafsize</span> <span class="o">=</span> <span class="mi">32</span><span class="o">;</span></code></pre></div> <p>Note: <a href="http://stackoverflow.com/q/7834111/562769">How can I prevent Eclipse from adding the ‘final’ for certain lines of Java code?</a></p> <h2>Commons CLI</h2> <h3>Installation</h3> <p>As for args4j, they offer a jar file which is in <a href="http://ftp-stud.hs-esslingen.de/pub/Mirrors/ftp.apache.org/dist//commons/cli/binaries/commons-cli-1.2-bin.tar.gz">commons-cli-1.2-bin.tar.gz</a> on the <a href="http://commons.apache.org/cli/download_cli.cgi">download-page</a>.</p> <p>If you just want to test if you have the required packages, copy this piece of code to Eclipse:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">CommandLineValues</span> <span class="o">{</span> <span class="n">CommandLineParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">BasicParser</span><span class="o">();</span> <span class="o">}</span></code></pre></div> <p>If you get the following error, you don’t have the required <code>org.apache.commons.cli</code>:</p> <div style="width: 441px" class="wp-caption aligncenter"><a href="../images/2012/07/java-eclipse-cli-lib-error.png"><img src="../images/2012/07/java-eclipse-cli-lib-error.png" alt="Java error mentioned by Eclipse: Missing org.apache.commons.cli" width="" height="" class="size-full wp-image-33201" /></a><p class="wp-caption-text">Java error mentioned by Eclipse: Missing org.apache.commons.cli</p></div> <h3>Usage examples</h3> <p>I have not found a single, complete and working usage example.</p> <h2>See also</h2> <ul> <li><a href="http://stackoverflow.com/q/367706/562769">Is there a good command line argument parser for Java?</a> - A lot of other command line parsers are mentioned for Java.</li> <li><a href="http://args4j.kohsuke.org/args4j/apidocs/">args4j JavaDoc</a></li> <li><a href="http://commons.apache.org/cli/api-release/index.html">Apache CLI JavaDoc</a></li> </ul> How to parse command line arguments in Python //martin-thoma.com/how-to-parse-command-line-arguments-in-python/ Wed, 18 Jul 2012 17:00:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-parse-command-line-arguments-in-python <h2>Argparse</h2> <blockquote>The <a href="http://docs.python.org/library/argparse.html">argparse module</a> makes it easy to write user-friendly command-line interfaces. The program defines what arguments it requires, and argparse will figure out how to parse those out of sys.argv. The argparse module also automatically generates help and usage messages and issues errors when users give the program invalid arguments.</blockquote> <h3>Installation</h3> <p>I had to install <code>python-argparse</code> on my old Ubuntu machine before I could use it.</p> <h3>Usage</h3> <p>As far as I’ve just tried it, you can use argparse very similar to optparse. See this <a href="https://github.com/MartinThoma/matrix-multiplication/commit/7af938c54fd2effee3efe74352b76f01d2e817e5#Python/ikjMultiplication.py">diff</a> for my switch from optparse to argparse for a simple script.</p> <p>It is very easy to add command line <del>options</del> argument (if you require an option, it would not be an option any more, would it? I’ll try to call them arguments from now on):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span> parser = ArgumentParser() <span style="color:#777"># Add more options if you like</span> parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-f</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--file</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">myFilenameVariable</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">write report to FILE</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-q</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--quiet</span><span style="color:#710">&quot;</span></span>, action=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">store_false</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">verbose</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#069">True</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">don't print status messages to stdout</span><span style="color:#710">&quot;</span></span>) args = parser.parse_args() print(args.myFilenameVariable) </pre></div> </div> </div> <p>Every option has some values like:</p> <ul> <li><a href="http://docs.python.org/library/argparse.html#dest">dest</a>: You will access the value of option with this variable</li> <li><a href="http://docs.python.org/library/argparse.html#help">help</a>: This text gets displayed whey someone uses <code>--help</code>.</li> <li><a href="http://docs.python.org/library/argparse.html#default">default</a>: If the command line argument was not specified, it will get this default value.</li> <li><a href="http://docs.python.org/library/argparse.html#action">action</a>: Actions tell optparse what to do when it encounters an option on the command line. <code>action</code> defaults to <code>store</code>. These actions are available: <ul> <li><strong>store</strong>: take the next argument (or the remainder of the current argument), ensure that it is of the correct type, and store it to your chosen destination dest.</li> <li><strong>store_true</strong>: store <code>True</code> in dest if this flag was set.</li> <li><strong>store_false</strong>: store <code>False</code> in dest if this flag was set.</li> <li><strong>store_const</strong>: store a constant value</li> <li><strong>append</strong>: append this option&rsquo;s argument to a list</li> <li><strong>count</strong>: increment a counter by one</li> <li><strong>callback</strong>: call a specified function</li> </ul> </li> <li><a href="http://docs.python.org/library/argparse.html#nargs">nargs</a>: ArgumentParser objects usually associate a single command-line argument with a single action to be taken. The nargs keyword argument associates a different number of command-line arguments with a single action.</li> <li><a href="http://docs.python.org/library/argparse.html#required">required</a>: Mark a command line argument as non-optional (required).</li> <li><a href="http://docs.python.org/library/argparse.html#choices">choices</a>: Some command-line arguments should be selected from a restricted set of values. These can be handled by passing a container object as the choices keyword argument to add_argument(). When the command line is parsed, argument values will be checked, and an error message will be displayed if the argument was not one of the acceptable values.</li> <li><a href="http://docs.python.org/library/argparse.html#type">type</a>: Use this command, if the argument is of another type (e.g. int or float).</li> </ul> <p>argparse automatically generates a help text. So if you call <code>python myScript.py --help</code> you will get something like that:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">usage: ikjMultiplication.py <span class="o">[</span>-h<span class="o">]</span> <span class="o">[</span>-i FILE<span class="o">]</span> ikjMatrix multiplication optional arguments: -h, --help show this <span class="nb">help </span>message and <span class="nb">exit</span> -i FILE input file with two matrices</code></pre></div> <h3>Example 1: Fibonacci</h3> <p>It is absolutely no problem to calculate the 100,000st Fibonacci number.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">mul</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">,</span> <span class="n">c</span> <span class="o">=</span> <span class="n">A</span> <span class="n">d</span><span class="p">,</span> <span class="n">e</span><span class="p">,</span> <span class="n">f</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">a</span><span class="o">*</span><span class="n">d</span> <span class="o">+</span> <span class="n">b</span><span class="o">*</span><span class="n">e</span><span class="p">,</span> <span class="n">a</span><span class="o">*</span><span class="n">e</span> <span class="o">+</span> <span class="n">b</span><span class="o">*</span><span class="n">f</span><span class="p">,</span> <span class="n">b</span><span class="o">*</span><span class="n">e</span> <span class="o">+</span> <span class="n">c</span><span class="o">*</span><span class="n">f</span> <span class="k">def</span> <span class="nf">pow</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="n">A</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&amp;</span> <span class="mi">1</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="nb">pow</span><span class="p">(</span><span class="n">mul</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">A</span><span class="p">),</span> <span class="n">n</span><span class="o">//</span><span class="mi">2</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="n">mul</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="nb">pow</span><span class="p">(</span><span class="n">mul</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">A</span><span class="p">),</span> <span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span><span class="o">//</span><span class="mi">2</span><span class="p">))</span> <span class="k">def</span> <span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">if</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="p">:</span> <span class="k">return</span> <span class="n">n</span> <span class="k">return</span> <span class="nb">pow</span><span class="p">((</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">0</span><span class="p">),</span> <span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)[</span><span class="mi">0</span><span class="p">]</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">argparse</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">argparse</span><span class="o">.</span><span class="n">ArgumentParser</span><span class="p">(</span><span class="n">description</span><span class="o">=</span><span class="s">&quot;Fibonacci-Script&quot;</span><span class="p">)</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_argument</span><span class="p">(</span><span class="s">&quot;-n&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&#39;N&#39;</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;print the N-th fibonacci number&quot;</span><span class="p">)</span> <span class="n">args</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="k">print</span> <span class="n">fib</span><span class="p">(</span><span class="n">args</span><span class="o">.</span><span class="n">n</span><span class="p">)</span></code></pre></div> <p>Note that it uses <code>type=int</code> not <code>type="int"</code> as it was in optparse.</p> <h3>Example 2: less</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">mul</span>(A, B): a, b, c = A d, e, f = B <span style="color:#080;font-weight:bold">return</span> a*d + b*e, a*e + b*f, b*e + c*f <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">pow</span>(A, n): <span style="color:#080;font-weight:bold">if</span> n == <span style="color:#00D">1</span>: <span style="color:#080;font-weight:bold">return</span> A <span style="color:#080;font-weight:bold">if</span> n &amp; <span style="color:#00D">1</span> == <span style="color:#00D">0</span>: <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">pow</span>(mul(A, A), n//<span style="color:#00D">2</span>) <span style="color:#080;font-weight:bold">else</span>: <span style="color:#080;font-weight:bold">return</span> mul(A, <span style="color:#369;font-weight:bold">pow</span>(mul(A, A), (n-<span style="color:#00D">1</span>)//<span style="color:#00D">2</span>)) <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">fib</span>(n): <span style="color:#080;font-weight:bold">if</span> n &lt; <span style="color:#00D">2</span>: <span style="color:#080;font-weight:bold">return</span> n <span style="color:#080;font-weight:bold">return</span> <span style="color:#369;font-weight:bold">pow</span>((<span style="color:#00D">1</span>,<span style="color:#00D">1</span>,<span style="color:#00D">0</span>), n-<span style="color:#00D">1</span>)[<span style="color:#00D">0</span>] <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">argparse</span> parser = argparse.ArgumentParser(description=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">less script</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-f</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--file</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">filename</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">write report to FILE</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-n</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">n</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">10</span>, type=<span style="color:#369;font-weight:bold">int</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">how many lines get printed</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-q</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--quiet</span><span style="color:#710">&quot;</span></span>, action=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">store_false</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">verbose</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#069">True</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">don't print status messages to stdout</span><span style="color:#710">&quot;</span></span>) args = parser.parse_args() <span style="color:#080;font-weight:bold">if</span> args.verbose: print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Will open file now and print %i lines.</span><span style="color:#710">&quot;</span></span> % args.n) f = <span style="color:#369;font-weight:bold">open</span>(args.filename, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">r</span><span style="color:#710">'</span></span>) <span style="color:#080;font-weight:bold">for</span> i <span style="color:#080;font-weight:bold">in</span> <span style="color:#369;font-weight:bold">xrange</span>(args.n): <span style="color:#080;font-weight:bold">print</span> f.readline() </pre></div> </div> </div> <h3 id="example-3-copy-paste-template">Example 3: copy-paste template</h3> <p>This is how I use it most of the time. I want to show defaults in help:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Example for a simple program with a command line parser.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">is_valid_file</span>(parser, arg): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> </span><span> Check if arg is a valid file that already exists on the file system.</span><span> </span><span> </span><span> Parameters</span><span> </span><span> ----------</span><span> </span><span> parser : argparse object</span><span> </span><span> arg : str</span><span> </span><span> </span><span> Returns</span><span> </span><span> -------</span><span> </span><span> arg</span><span> </span><span> </span><span style="color:black">&quot;&quot;&quot;</span></span> arg = os.path.abspath(arg) <span style="color:#080;font-weight:bold">if</span> <span style="color:#080;font-weight:bold">not</span> os.path.exists(arg): parser.error(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">The file %s does not exist!</span><span style="color:#710">&quot;</span></span> % arg) <span style="color:#080;font-weight:bold">else</span>: <span style="color:#080;font-weight:bold">return</span> arg <span style="color:#080;font-weight:bold">def</span> <span style="color:#06B;font-weight:bold">get_parser</span>(): <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span>Get parser object for script xy.py.</span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#080;font-weight:bold">from</span> <span style="color:#B44;font-weight:bold">argparse</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">ArgumentParser</span>, <span style="color:#B44;font-weight:bold">ArgumentDefaultsHelpFormatter</span> parser = ArgumentParser(description=__doc__, formatter_class=ArgumentDefaultsHelpFormatter) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-f</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--file</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">filename</span><span style="color:#710">&quot;</span></span>, type=<span style="color:#080;font-weight:bold">lambda</span> x: is_valid_file(parser, x), help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">write report to FILE</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-n</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">n</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">10</span>, type=<span style="color:#369;font-weight:bold">int</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">how many lines get printed</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-q</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--quiet</span><span style="color:#710">&quot;</span></span>, action=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">store_false</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">verbose</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#069">True</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">don't print status messages to stdout</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">return</span> parser <span style="color:#080;font-weight:bold">if</span> __name__ == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">__main__</span><span style="color:#710">&quot;</span></span>: args = get_parser().parse_args() </pre></div> </div> </div> <h2>Optparse</h2> <div class="info">Deprecated since version 2.7: The optparse module is deprecated and will not be developed further; development will continue with the argparse module.</div> <p>Parsing command line arguments with <a href="http://docs.python.org/library/optparse.html">optparse</a> was very easy, but as it is deprecated and argparse works almost the same way, I will not make any examples. Just use argparse.</p> <h2>See also</h2> <ul> <li><a href="http://stackoverflow.com/q/3217673/562769">Why use argparse rather than optparse?</a></li> <li><a href="http://stackoverflow.com/q/8387924/562769">Python argparse and bash completion</a></li> </ul> Java Puzzle #3: Rounding //martin-thoma.com/java-puzzle-3-rounding/ Tue, 17 Jul 2012 17:00:53 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-3-rounding <h2>The puzzle</h2> <p>What is the output of the following script:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">x</span> <span class="o">=</span> <span class="mf">0.4999999999999999</span><span class="o">;</span> <span class="kt">double</span> <span class="n">y</span> <span class="o">=</span> <span class="mf">0.49999999999999992</span><span class="o">;</span> <span class="kt">double</span> <span class="n">z</span> <span class="o">=</span> <span class="mf">0.49999999999999994</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">x</span> <span class="o">+</span> <span class="s">&quot; rounded is &quot;</span> <span class="o">+</span> <span class="n">Math</span><span class="o">.</span><span class="na">round</span><span class="o">(</span><span class="n">x</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">y</span> <span class="o">+</span> <span class="s">&quot; rounded is &quot;</span> <span class="o">+</span> <span class="n">Math</span><span class="o">.</span><span class="na">round</span><span class="o">(</span><span class="n">y</span><span class="o">));</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">z</span> <span class="o">+</span> <span class="s">&quot; rounded is &quot;</span> <span class="o">+</span> <span class="n">Math</span><span class="o">.</span><span class="na">round</span><span class="o">(</span><span class="n">z</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">0.4999999999999999 rounded is 0 0.49999999999999994 rounded is 1 0.49999999999999994 rounded is 1</code></pre></div> <h2>Explanation</h2> <p>It’s a <a href="http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=6430675">bug</a>.</p> <p>See also: <a href="http://stackoverflow.com/q/9902968/562769">Why does Math.round(0.49999999999999994) return 1</a></p> Java Puzzle #2: Integers and Floats //martin-thoma.com/java-puzzle-2-integers-and-floats/ Mon, 16 Jul 2012 17:00:35 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-2-integers-and-floats <h2>Basics</h2> <p>As you might know, Americans measure the temperature in <a href="http://en.wikipedia.org/wiki/Fahrenheit">Fahrenheit</a>. I’m not quite sure, but I guess the rest of the world uses <a href="http://en.wikipedia.org/wiki/Celsius">Celsius</a>.</p> <p>0° C is the temperature when water freezes. 100° C is the temperature when water boils.</p> <p>0° F is the lowest temperature of the winter 1708/1709 in <a href="http://en.wikipedia.org/wiki/Gda%C5%84sk">Gdańsk</a>. 32° F is the temperature when water boils.</p> <p>If you want to calculate the temperature <code>$T_C$</code> in °C from <code>$T_F$</code> in °F you can use this formula: <code>$T_C = (T_F &amp;minus; 32) &amp;middot; \frac{5}{9}$</code></p> <h2>The puzzle</h2> <p>What is the output of the following script?</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">static</span> <span class="kt">double</span> <span class="nf">fahrenheitToCelsius</span><span class="o">(</span><span class="kt">double</span> <span class="n">fahrenheit</span><span class="o">)</span> <span class="o">{</span> <span class="k">return</span> <span class="o">(</span><span class="n">fahrenheit</span> <span class="o">-</span> <span class="mi">32</span><span class="o">)</span> <span class="o">*</span> <span class="o">(</span><span class="mi">5</span> <span class="o">/</span> <span class="mi">9</span><span class="o">);</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">double</span> <span class="n">fahrenheit</span> <span class="o">=</span> <span class="mi">100</span><span class="o">;</span> <span class="kt">double</span> <span class="n">celsius</span> <span class="o">=</span> <span class="n">fahrenheitToCelsius</span><span class="o">(</span><span class="n">fahrenheit</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">format</span><span class="o">(</span><span class="s">&quot;%.2f&amp;deg; Fahrenheit is %.2f&amp;deg; C\n&quot;</span><span class="o">,</span> <span class="n">fahrenheit</span><span class="o">,</span> <span class="n">celsius</span><span class="o">);</span> <span class="n">fahrenheit</span> <span class="o">=</span> <span class="mi">30</span><span class="o">;</span> <span class="n">celsius</span> <span class="o">=</span> <span class="n">fahrenheitToCelsius</span><span class="o">(</span><span class="n">fahrenheit</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">format</span><span class="o">(</span><span class="s">&quot;%.2f&amp;deg; Fahrenheit is %.2f&amp;deg; C\n&quot;</span><span class="o">,</span> <span class="n">fahrenheit</span><span class="o">,</span> <span class="n">celsius</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">100.00<span class="p">&amp;</span>deg<span class="p">;</span> Fahrenheit is 0.00<span class="p">&amp;</span>deg<span class="p">;</span> C 30.00<span class="p">&amp;</span>deg<span class="p">;</span> Fahrenheit is -0.00<span class="p">&amp;</span>deg<span class="p">;</span> C</code></pre></div> <h2>Explanation</h2> <p>The problem is integer division.</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">format</span><span class="o">(</span><span class="s">&quot;5 / 9 = %.2f\n&quot;</span><span class="o">,</span> <span class="o">(</span><span class="kt">double</span><span class="o">)</span> <span class="o">(</span><span class="mi">5</span> <span class="o">/</span> <span class="mi">9</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>This outputs:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="m">5</span> / <span class="nv">9</span> <span class="o">=</span> 0.00</code></pre></div> <p>So you are multiplying with <code>$\pm 0$</code> instead of <code>$0.55555$</code>.</p> Algorithmen-Klausur //martin-thoma.com/algorithmen-klausur/ Mon, 16 Jul 2012 09:00:25 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/algorithmen-klausur <p>Für die Klausur in Algorithmen I sollte man Folgendes auf jeden Fall wissen:</p> <ul> <li>Wie sind die Landau-Symbole `$\cal O(f(n)), \Theta(f(n)), \Omega(f(n))$` definiert? &rarr; <a title="Definitionen aus GBI" href="../definitionen-aus-gbi/#Komplexittstheorie">Antwort</a></li> <li>Wie lautet das Master-Theorem? &rarr; <a href="http://de.wikipedia.org/wiki/Master-Theorem#Allgemeine_Form">Antwort</a></li> <li>Wie funktioniert der Bellman-Ford-Algorithmus und was macht er? &rarr; <a href="http://de.wikipedia.org/wiki/Bellman-Ford-Algorithmus">Antwort</a></li> <li>Wie funktioniert der Dijkstra-Algorithmus und was macht er? &rarr; <a href="http://de.wikipedia.org/wiki/Dijkstra-Algorithmus">Antwort</a></li> <li>Wie funktioniert der Algorithmus von Kruskal und was macht er? &rarr; <a href="http://de.wikipedia.org/wiki/Algorithmus_von_Kruskal">Antwort</a></li> <li>Wie funktioniert der Algorithmus von Prim und was macht er? &rarr; <a href="http://de.wikipedia.org/wiki/Algorithmus_von_Prim">Antwort</a></li> <li>Was ist ein Heap, ein B-Baum, ein Digitaler Baum und was ein Suchbaum? &rarr; <a href="../ubersicht-uber-datenstrukturen/">Antwort</a></li> <li>Sei `$A := $` {Insertionsort, Quicksort, Mergesort, Heapsort, Selectionsort}. Beantworte und begr&uuml;nde f&uuml;r `$x \in A$` folgende Fragen: <ul> <li>Wie funktioniert x?</li> <li>Ist x stabil?</li> <li>Arbeitet x in-place?</li> <li>Hat x im Worst-Case optimales Laufzeitverhalten?</li> <li>Hat x im Worst-Case optimales Speicherplatzverhalten?</li> </ul> &rarr; <a href="../ubersicht-uber-sortieralgorithmen/" title="&Uuml;bersicht &uuml;ber Sortieralgorithmen">Antwort</a> </li> <li>Wie funktioniert Radixsort? &rarr; <a href="http://de.wikipedia.org/wiki/Radixsort">Antwort</a></li> <li>Warum ist Radixsort und <a href="http://de.wikipedia.org/wiki/Countingsort">Countingsort</a> nur schlecht mit den Sortieralgorithmen aus vergleichbar?</li> <li>Welches Worst-Case Laufzeitverhalten hat die <a href="http://de.wikipedia.org/wiki/Breitensuche#Laufzeit">Breitensuche</a>, welches die <a href="http://de.wikipedia.org/wiki/Tiefensuche#Laufzeit">Tiefensuche</a>?</li> </ul> <h2>Some Random Facts</h2> <p>Das ist ein Graph, bei dem der Algorithmus von Dijkstra fehlschlägt:</p> <div style="width: 288px" class="wp-caption aligncenter"><a href="../images/2012/07/dijkstra-fail.gif"><img src="//martin-thoma.com/captions/dijkstra-fail.gif" alt="Minimales Beispiel f&uuml;r einen Graphen, bei dem der Dijkstra-Algorithmus fehlschl&auml;gt." width="278" height="278" class=" wp-image-31761 " /></a><p class="wp-caption-text">Minimales Beispiel f&uuml;r einen Graphen, bei dem der Dijkstra-Algorithmus fehlschl&auml;gt.</p></div> <h2>Termine</h2> <p><strong>Datum</strong>: Dienstag, der 31.07.2012 um 17:00 Uhr <strong>Ort</strong>:</p> <blockquote>Die Sitze sind alphabetisch nach Ihrem Nachnamen eingeteilt: A-C H&ouml;rsaal am Fasanengarten(50.35) D-J Gerthsen H&ouml;rsaal(30.21) K-O Audimax(30.95) P-R Daimler(10.21) S Benz(10.21) T-V Tulla(11.40) W-Z Neue Chemie(30.46) </blockquote> <p><strong>Dauer</strong>: 120 min. (<a href="https://studium.kit.edu/sites/vab/0x32F499D5541AEE45A9509B71A4796335/Start/homepage.aspx">Quelle</a>) <strong>Punkte</strong>: 60 <strong>Übungsschein</strong>: Gibt es nicht. Bonuspunkte gibt es auch nicht. <strong>Sitzplatzverteilung</strong>: <a href="https://studium.kit.edu/sites/vab/0x32F499D5541AEE45A9509B71A4796335/Vorlesungsunterlagen/Forms/AllItems.aspx">hier</a></p> <h2>Nicht vergessen</h2> <ul> <li>Studentenausweis</li> <li>Kugelschreiber</li> </ul> <h2>Klausurergebnisse</h2> <p>Die Klausurergebnisse hängen im SCC, 3. OG, aus.</p> <p><strong>Klausureinsicht</strong>: 23.08.2012 und 24.08.2012</p> Übersicht über Sortieralgorithmen //martin-thoma.com/ubersicht-uber-sortieralgorithmen/ Sun, 15 Jul 2012 15:00:12 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ubersicht-uber-sortieralgorithmen <p>Eine Übersicht über gängige Sortieralgorithmen:</p> <h2>Vergleichsbasiert</h2> <table> <tr> <th rowspan="2" style="border-bottom: #000 double 3px;">Name</th> <th colspan="3" style="background-color:#cf3;text-align:center">Laufzeit</th> <th rowspan="2" style="border-bottom: #000 double 3px;">stabil</th> <th rowspan="2" style="border-bottom: #000 double 3px;">in-place</th> </tr> <tr> <th style="background-color:#cf3;border-bottom: #000 double 3px;">B</th> <th style="background-color:#cf3;border-bottom: #000 double 3px;">AVG</th> <th style="background-color:#cf3;border-bottom: #000 double 3px;">W</th> </tr> <tr> <th><a href="http://de.wikipedia.org/wiki/Selectionsort">Selectionsort</a></th> <td>`$\Theta (n^2)$`</td> <td>`$\Theta (n^2)$`</td> <td>`$\Theta (n^2)$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="size-full wp-image-12931" /></a><small>[1]</small></td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <tr> <th><a href="http://de.wikipedia.org/wiki/Bubblesort">Bubblesort</a></th> <td>`$\Theta (n)$`</td> <td>`$\cal{O}(n^2)$`</td> <td>`$\Theta (n^2)$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></a></td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <tr> <th><a href="http://de.wikipedia.org/wiki/Insertionsort">Insertionsort</a></th> <td>`$\Theta (n)$`</td> <td>`$\Theta (n^2)$`</td> <td>`$\Theta (n^2)$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></a></td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <tr> <th><a href="http://de.wikipedia.org/wiki/Quicksort">Quicksort</a></th> <td>`$\Theta (n \cdot log(n))$`</td> <td>`$\Theta (n \cdot log(n))$`</td> <td>`$\Theta (n^2)$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="size-full wp-image-12931" /> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <tr> <th><a href="http://de.wikipedia.org/wiki/Heapsort">Heapsort</a></th> <td>`$\cal{O}(n \cdot log(n))$`</td> <td>`$\cal{O}(n \cdot log(n))$`</td> <td>`$\cal{O}(n \cdot log(n))$`</td> <td><a href="../images/2012/01/no.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></a></td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <tr> <th><a href="http://de.wikipedia.org/wiki/Mergesort">Mergesort</a></th> <td>`$\Theta (n \cdot log(n))$`</td> <td>`$\Theta (n \cdot log(n))$`</td> <td>`$\Theta (n \cdot log(n))$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <td><a href="../images/2012/01/no.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></a><small>[2]</small></td> <tr> <th><a href="http://de.wikipedia.org/wiki/Timsort">Timsort</a></th> <td>`$\Theta (n)$`</td> <td>`$\cal{O}(n \cdot log(n))$`</td> <td>`$\cal{O}(n \cdot log(n))$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /> <td><a href="../images/2012/01/no.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></a></td> Ich habe - bis auf Timsort - jeden dieser Algorithmen in Python implementiert, siehe <a href="https://github.com/MartinThoma/algorithms/blob/master/sorting.py">Python-Code f&uuml;r Sortieralgorithmen</a>. <small>[1]</small>: Beispiel: A = [2, 2, 1] <small>[2]</small>: in der regel nicht in-place, kann aber auch in-place implementiert werden. <h2>Nicht Vergleichsbasiert</h2> Es sei <ul> <li>`$n$` die Anzahl der Zahlen, </li> <li>`$d$` die maximale Anzahl der Stellen</li> <li>`$k$` die Anzahl der m&ouml;glichen Zeichen (die Basis).</li> </ul> Dann gilt: <table> <tr> <th style="border-bottom: #000 double 3px;">Name</th> <th style="border-bottom: #000 double 3px;text-align:center">Worst-Case Laufzeit</th> <th style="border-bottom: #000 double 3px;">stabil</th> <th style="border-bottom: #000 double 3px;">in-place</th> </tr> <tr> <th><a href="http://de.wikipedia.org/wiki/Radixsort">Radixsort</a></th> <td>`$\cal{O}(d \cdot (n+k))$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></a></td> <td><a href="../images/2012/01/no.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></a></td> </tr> <tr> <th><a href="http://de.wikipedia.org/wiki/Countingsort">Countingsort</a></th> <td>`$\cal{O}(n+k)$`</td> <td><a href="../images/2012/01/yes.png"><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></a></td> <td><a href="../images/2012/01/no.png"><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></a></td> </tr> </table> <h2>Siehe auch</h2> <ul> <li><a href="http://www.sorting-algorithms.com/">Sorting Algorithm Animations</a>: Eine tolle Website, die veranschaulicht, wie verschiedene Sortieralgorithmen funktionieren.</li> <li><a href="http://www.youtube.com/watch?v=t8g-iYGHpEA">What different sorting algorithms sound like</a></li> </ul> </a></td></tr></a></td></tr></a></td></tr></a></td></a></td></tr></a></td></tr></a></td></tr></a></td></tr></table> How to search for mathematical symbols in LaTeX //martin-thoma.com/how-to-search-for-mathematical-symbols-in-latex/ Sat, 14 Jul 2012 19:00:44 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-search-for-mathematical-symbols-in-latex <h2>Detexify</h2> <p>The easiest way to search for a math symbol is <a href="http://detexify.kirelabs.org/classify.html">Detexify</a>. This webservices allows you to draw the symbol. It looks like this:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/07/detexify.png"><img src="../images/2012/07/detexify.png" alt="Detexify - A webservice for finding LaTeX symbols." width="" height="" class="size-full wp-image-31471" /></a><p class="wp-caption-text">Detexify - A webservice for finding LaTeX symbols.</p></div> <h2>Symbol tables</h2> <h3>Arrows</h3> <table> <tr> <td><span>\(\rightarrow\)</span></td><td>\rightarrow</td> <td><span>\(\leftarrow\)</span></td><td>\leftarrow</td> <td><span>\(\Rightarrow\)</span></td><td>\Rightarrow</td> <td><span>\(\Leftarrow\)</span></td><td>\Leftarrow</td> </tr> <tr> <td><span>\(\leftrightarrow\)</span></td><td>\leftrightarrow</td> <td><span>\(\Leftrightarrow\)</span></td><td>\Leftrightarrow</td> <td><span>\(\nRightarrow\)</span></td><td>\nRightarrow</td> <td><span>\(\nrightarrow\)</span></td><td>\nrightarrow</td> </tr> <tr> <td><span>\(\leadsto\)</span></td><td>\leadsto</td> <td><span>\(\mapsto\)</span></td><td>\mapsto</td> <td>.</td><td>.</td> <td>.</td><td>.</td> </tr> </table> <h3>Greek</h3> <table> <tr> <td><span>\(\alpha\)</span></td><td>\alpha</td> <td><span>\(\beta\)</span></td><td>\beta</td> <td><span>\(\gamma\)</span></td><td>\gamma</td> <td><span>\(\delta\)</span></td><td>\delta</td> </tr> <tr> <td><span>\(\zeta\)</span></td><td>\zeta</td> <td><span>\(\eta\)</span></td><td>\eta</td> <td><span>\(\theta\)</span></td><td>\theta</td> <td><span>\(\epsilon, \varepsilon\)</span></td><td>\epsilon, \varepsilon</td> </tr> <tr> <td><span>\(\iota\)</span></td><td>\iota</td> <td><span>\(\kappa\)</span></td><td>\kappa</td> <td><span>\(\lambda\)</span></td><td>\lambda</td> <td><span>\(\mu\)</span></td><td>\mu</td> </tr> <tr> <td><span>\(\nu\)</span></td><td>\nu</td> <td><span>\(\xi\)</span></td><td>\xi</td> <td>o</td><td>o</td> <td><span>\(\pi\)</span></td><td>\pi</td> </tr> <tr> <td><span>\(\rho\)</span></td><td>\rho</td> <td><span>\(\sigma\)</span></td><td>\sigma</td> <td><span>\(\tau\)</span></td><td>\tau</td> <td><span>\(\upsilon\)</span></td><td>\upsilon</td> </tr> <tr> <td><span>\(\phi\)</span></td><td>\phi</td> <td><span>\(\chi\)</span></td><td>\chi</td> <td><span>\(\psi\)</span></td><td>\psi</td> <td><span>\(\omega, \Omega\)</span></td><td>\omega, \Omega</td> </tr> <tr> <td><span>\(\Phi\)</span></td><td>\Phi</td> <td><span>\(\varphi\)</span></td><td>\varphi</td> <td>.</td><td>.</td> <td>.</td><td>.</td> </tr> <tr> <td><span>\(\Lambda\)</span></td><td>\Lambda</td> <td><span>\(\Delta\)</span></td><td>\Delta</td> <td>.</td><td>.</td> <td>.</td><td>.</td> </tr> </table> <h3>Operations</h3> <table> <tr> <td><span>\(\cdot\)</span></td><td>\cdot</td> <td><span>\(\oplus\)</span></td><td>\oplus</td> <td><span>\(\times\)</span></td><td>\times</td> <td><span>\(\nabla\)</span></td><td>\nabla</td> </tr> <tr> <td><span>\(\pm\)</span></td><td>\pm</td> <td><span>\(\mp\)</span></td><td>\mp</td> <td><span>\(\cup\)</span></td><td>\cup</td> <td><span>\(\cap\)</span></td><td>\cap</td> </tr> </table> <h3>Relations</h3> <table> <tr> <td><span>\(\approx\)</span></td><td>\approx</td> <td><span>\(\sim\)</span></td><td>\sim</td> <td><span>\(\cong\)</span></td><td>\cong</td> <td><span>\(\neq\)</span></td><td>\neq</td> </tr> </table> <h3>Calligraphic Letters</h3> <table> <tr> <td><span>\(\cal{O}\)</span></td><td>\cal{O}</td> <td><span>\(\mathfrak{M}\)</span></td><td>\mathfrak{O}</td> <td><span>\(\mathfrak{R}\)</span></td><td>\mathfrak{R}</td> </tr> </table> <h3>Sets</h3> <table> <tr> <td><span>\(\mathbb{N}\)</span></td><td>\mathbb{N}</td> <td><span>\(\mathbb{Z}\)</span></td><td>\mathbb{Z}</td> <td><span>\(\mathbb{R}\)</span></td><td>\mathbb{R}</td> <td><span>\(\mathbb{C}\)</span></td><td>\mathbb{C}</td> </tr> <tr> <td><span>\(\mathbb{A}\)</span></td><td>\mathbb{A}</td> <td><span>\(\cap\)</span></td><td>\cap</td> <td><span>\(\cup\)</span></td><td>\cup</td> <td><span>\(\in\)</span></td><td>\in</td> </tr> <tr> <td><span>\(\subseteq\)</span></td><td>\subseteq</td> <td><span>\(\subsetneq\)</span></td><td>\subsetneq</td> <td><span>\(\notin\)</span></td><td>\notin</td> <td><span>\(\bigcup\)</span></td><td>\bigcup</td> </tr> </table> <h3>Other</h3> <p>You might need <code>\qed</code>, <code>\qedsymbol</code>, <code>\blacksquare</code> for proofs. It is the <a href="http://en.wikipedia.org/wiki/Tombstone_(typography)">Tombstone</a> <span>\(\blacksquare\)</span></p> <p>I’ve recently needed <span>\(\dots, \ddots, \vdots\)</span> (<code>\dots</code>, <code>\ddots</code>, <code>\vdots</code>) for a visualization in a matrix. Note that you can write … instead of <code>\dots</code>, but you’ll lose the semantics.</p> <h2>See also</h2> <ul> <li><a href="http://www.tex.ac.uk/tex-archive/info/symbols/comprehensive/symbols-a4.pdf">List of symbols</a> - 164 pages of symbols</li> <li><a href="http://en.wikipedia.org/wiki/Help:Displaying_a_formula">Displaying a formula</a></li> </ul> When is matrix multiplication commutative? //martin-thoma.com/when-is-matrix-multiplication-commutative/ Sat, 14 Jul 2012 10:49:48 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/when-is-matrix-multiplication-commutative <p>Matrix multiplication in general is not commutative. Here is an example:</p> <p><code>$A, B \in R^{2 \times 2}$</code> <code>$A := \begin{pmatrix} 1 &amp; 2 \\ 3 &amp; 4 \end{pmatrix}$</code> <code>$B := \begin{pmatrix} 5 &amp; 6 \\ 7 &amp; 8 \end{pmatrix}$</code></p> <p><code>$A \cdot B = \begin{pmatrix} 19 &amp; 22 \\ 43 &amp; 50 \end{pmatrix} \neq \begin{pmatrix} 23 &amp; 34 \\ 31 &amp; 46 \end{pmatrix} = B \cdot A$</code></p> <h2>When is 2x2 matrix multiplication commutative?</h2> <p><code>$\begin{pmatrix} a &amp; b \\ c &amp; d \end{pmatrix} \cdot \begin{pmatrix} e &amp; f \\ g &amp; h \end{pmatrix} = \begin{pmatrix} ae + bg &amp; af + bh \\ ce + dg &amp; cf + dh \end{pmatrix}$</code></p> <p><code>$\begin{pmatrix} e &amp; f \\ g &amp; h \end{pmatrix} \cdot \begin{pmatrix} a &amp; b \\ c &amp; d \end{pmatrix} = \begin{pmatrix} ae + cf &amp; be + df \\ ag + ch &amp; bg + dh \end{pmatrix}$</code></p> <p>So you get four equations: <code>$\begin{eqnarray*} I) &amp; ae + bg &amp;= ae + cf &amp;\Leftrightarrow bg = cf \\ II) &amp; af + bh &amp;= be + df\\ III) &amp; ce + dg &amp;= ag + ch\\ IV) &amp; cf + dh &amp;= bg + dh &amp;\Leftrightarrow cf = bg \end{eqnarray*}$</code></p> <p>You might note that (I) is the same as (IV). So you have those equations: <code>$\begin{eqnarray*} I) &amp; bg = cf \\ II) &amp; af + bh &amp;= be + df &amp; \Leftrightarrow f (a - d) = b (e - h)\\ III) &amp; ce + dg &amp;= ag + ch &amp; \Leftrightarrow g (a - d) = c (e - h) \end{eqnarray*}$</code></p> <h3>Case #1: a != d and e != h</h3> <p><code>$\begin{eqnarray*} I) &amp; bg &amp;= cf \\ II) &amp; \frac{f}{g} &amp;= \frac{b}{c} \Leftrightarrow cf = bg \end{eqnarray*}$</code></p> <p>Now (I) and (II) are essentially the same. So we only demand that <code>$ bg = cf$</code> and <code>$a \neq d$</code> and <code>$e \neq h$</code> for commutative matrix multiplication of <code>$2 \times 2$</code> matrices.</p> <h3>Case #2.1: a == d</h3> <p><code>$\begin{eqnarray*} I) &amp; bg &amp;= cf \\ II) &amp; 0 &amp;= b (e - h)\\ III) &amp; 0 &amp;= c (e - h) \end{eqnarray*}$</code></p> <p>So you end up with: (<code>$e = h$</code> and <code>$bg = cf$</code>) or (<code>$b = c = 0$</code>)</p> <h3>Case #2.2: e == h</h3> <p><code>$\begin{eqnarray*} I) &amp; bg &amp;= cf \\ II) &amp; f (a - d) &amp;= 0\\ III) &amp; g (a - d) &amp;= 0 \end{eqnarray*}$</code></p> <p>So you end up with: (<code>$a = d$</code> and <code>$bg = cf$</code>) or (<code>$f = g = 0$</code>)</p> <h2>Special Cases</h2> <p>Matrix multiplication is always commutative if …</p> <ul> <li>... one matrix is the <a href="http://en.wikipedia.org/wiki/Identity_matrix">Identity matrix</a>.</li> <li>... one matrix is the <a href="http://en.wikipedia.org/wiki/Zero_matrix">Zero matrix</a>.</li> <li>... both matrices are <a href="http://en.wikipedia.org/wiki/Rotation_matrix">rotation matrices</a>. (basically case #2)</li> <li>... both matrices are <a href="http://en.wikipedia.org/wiki/Diagonal_matrix">Diagonal matrices</a>.</li> </ul> <h2>Simultaneous diagonalization</h2> <p>Two matrices <code>$A, B \in R^{n \times n}$</code> are called simultaneous diagonalizable <code>$: \Leftrightarrow$</code> one matrix <code>$S \in R^{n \times n}$</code> exists, such that <code>$D_A = S^{-1} \cdot A \cdot S$</code> and <code>$D_B = S^{-1} \cdot B \cdot S$</code> with <code>$D_A$</code> and <code>$D_B$</code> are diagonal matrices.</p> <p><strong>Statement</strong>: <code>$A, B \in \mathbb{R}^{n \times n}$</code> are simultaneous diagonalizable <code>$\Rightarrow A \cdot B = B \cdot A$</code> <strong>Proof</strong>: As A and B are simultaneous diagonalizable, a matrix <code>$T \in \mathbb{R}^{n \times n}$</code> exists, such that <code>$D_A = S^{-1} \cdot A \cdot S$</code> and <code>$D_B = S^{-1} \cdot B \cdot S$</code> with <code>$D_A$</code> and <code>$D_B$</code> are diagonal matrices.</p> <p><code>$ \begin{align} \Rightarrow A \cdot B &amp;= S \cdot D_A S^{-1} \cdot S \cdot D_B \cdot S^{-1} \\ &amp;= S \cdot D_A \cdot D_B \cdot S^{-1} \\ &amp;= S \cdot D_B \cdot D_A \cdot S^{-1} \\ &amp;= S \cdot D_B \cdot S^{-1} \cdot S \cdot D_A \cdot S^{-1} \\ &amp;= B \cdot A \blacksquare \end{align} $</code></p> <p><strong>Statement</strong>: <code>$A \cdot B = B \cdot A \nRightarrow A, B \in \mathbb{R}^{n \times n}$</code> are simultaneous diagonalizable. <strong>Proof</strong>: by Counter-Example <code>$\begin{pmatrix}0 &amp; 1 \\ 0 &amp; 0\end{pmatrix} \cdot \begin{pmatrix}1 &amp; 0 \\ 0 &amp; 1\end{pmatrix} = \begin{pmatrix}1 &amp; 0 \\ 0 &amp; 1\end{pmatrix} \cdot \begin{pmatrix}0 &amp; 1 \\ 0 &amp; 0\end{pmatrix}$</code>, but <code>$\begin{pmatrix}0 &amp; 1 \\ 0 &amp; 0\end{pmatrix}$</code> is not diagonalizable. <code>$\blacksquare$</code></p> <h2>See also</h2> <ul> <li><a href="http://math.stackexchange.com/q/170241/6876">When is matrix multiplication commutative?</a> on math.stackexchange.com</li> </ul> GOTO in Python, Java and C++ //martin-thoma.com/goto-in-python-java-and-cpp/ Thu, 12 Jul 2012 22:04:01 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/goto-in-python-java-and-cpp <p><a href="http://en.wikipedia.org/wiki/Goto">GOTO</a> is a statement of the early beginnings of programming. It is rarely used in high-level code today. Code that makes use of it is called <a href="http://en.wikipedia.org/wiki/Spaghetti_code">Spaghetti code</a> by some people. I have almost never seen goto statements in code, so I’ve been curious about them.</p> <div style="width: 543px" class="wp-caption aligncenter"><a href="../images/2012/07/xkcd-goto.png"><img src="//martin-thoma.com/captions/xkcd-goto.png" alt="GOTO from xkcd.com" width="533" height="145" class=" wp-image-30341 " /></a><p class="wp-caption-text">GOTO from xkcd.com</p></div> <h2>Python</h2> <p>Python does NOT offer GOTO. However, somebody made a GOTO module for April Fools’ Day. See <a href="http://stackoverflow.com/q/6959360/562769"><code>goto</code> in Python</a> if you’re still interested.</p> <h2>Java</h2> <blockquote>Java has no goto statement. Studies illustrated that goto is (mis)used more often than not simply "because it's there". Eliminating goto led to a simplification of the language--there are no rules about the effects of a goto into the middle of a for statement, for example. Studies on approximately 100,000 lines of C code determined that roughly 90 percent of the goto statements were used purely to obtain the effect of breaking out of nested loops. As mentioned above, multi-level break and continue remove most of the need for goto statements.</blockquote> <p>Source: <a href="http://java.sun.com/docs/white/langenv/Simple.doc2.html#5550">java.sun.com</a></p> <h2>C++</h2> <p>GOTO works in C++. Here is a minimal example:</p> <h3>Minimal Example</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(){</span> <span class="kt">int</span> <span class="n">test</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="nl">start</span><span class="p">:;</span> <span class="k">if</span> <span class="p">(</span><span class="n">test</span> <span class="o">&gt;</span> <span class="mi">10</span><span class="p">)</span> <span class="p">{</span> <span class="k">goto</span> <span class="n">end</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">test</span> <span class="o">+=</span> <span class="mi">7</span><span class="p">;</span> <span class="k">goto</span> <span class="n">start</span><span class="p">;</span> <span class="p">}</span> <span class="nl">end</span><span class="p">:;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;test: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">test</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">test</span>: 14</code></pre></div> <h3>Euclidean GCD algorithm</h3> <p>Most of you might know the <a href="http://en.wikipedia.org/wiki/Euclidean_algorithm">euclidean algorithm</a> for calculating the greatest common divisor in a version like this one:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">euclidGCD</span><span class="p">(</span><span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="kt">int</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">while</span> <span class="p">(</span><span class="n">b</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">m</span> <span class="o">=</span> <span class="n">a</span> <span class="o">%</span> <span class="n">b</span><span class="p">;</span> <span class="n">a</span> <span class="o">=</span> <span class="n">b</span><span class="p">;</span> <span class="n">b</span> <span class="o">=</span> <span class="n">m</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">a</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(){</span> <span class="c1">// Outputs 20</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;GCD of 340 and 32760: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">euclidGCD</span><span class="p">(</span><span class="mi">340</span><span class="p">,</span> <span class="mi">32760</span><span class="p">)</span> <span class="o">&lt;&lt;</span><span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Here is a goto-version that works perfectly fine:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">euclidGCD</span><span class="p">(</span><span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="kt">int</span> <span class="n">b</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">b</span> <span class="o">&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="k">goto</span> <span class="n">b_larger</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="mi">1</span><span class="p">)</span> <span class="p">{</span> <span class="n">a</span> <span class="o">=</span> <span class="n">a</span> <span class="o">%</span> <span class="n">b</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">a</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="k">return</span> <span class="n">b</span><span class="p">;</span> <span class="nl">b_larger</span><span class="p">:</span> <span class="n">b</span> <span class="o">=</span> <span class="n">b</span> <span class="o">%</span> <span class="n">a</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">b</span> <span class="o">==</span> <span class="mi">0</span><span class="p">)</span> <span class="k">return</span> <span class="n">a</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(){</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;GCD of 340 and 32760: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">euclidGCD</span><span class="p">(</span><span class="mi">340</span><span class="p">,</span> <span class="mi">32760</span><span class="p">)</span> <span class="o">&lt;&lt;</span><span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Source: <a href="http://en.literateprograms.org/Euclidean_algorithm_(C)">literateprograms.org</a></p> <h3>Try bad things</h3> <p>You can’t jump into a function:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">myFunction</span><span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="p">)</span> <span class="p">{</span> <span class="n">i</span> <span class="o">+=</span> <span class="mi">1</span><span class="p">;</span> <span class="nl">inFunctionLabel</span><span class="p">:;</span> <span class="n">i</span> <span class="o">+=</span> <span class="mi">1</span><span class="p">;</span> <span class="k">return</span> <span class="n">i</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(){</span> <span class="kt">int</span> <span class="n">test</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">goto</span> <span class="n">inFunctionLabel</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;test: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">test</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Compiler error:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gotoExample.cpp: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>int myFunction<span class="o">(</span>int<span class="o">)</span><span class="p">&amp;</span>rsquo<span class="p">;</span>: gotoExample.cpp:7: warning: label <span class="p">&amp;</span>lsquo<span class="p">;</span>inFunctionLabel<span class="p">&amp;</span>rsquo<span class="p">;</span> defined but not used gotoExample.cpp: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>int main<span class="o">()</span><span class="p">&amp;</span>rsquo<span class="p">;</span>: gotoExample.cpp:15: error: label <span class="p">&amp;</span>lsquo<span class="p">;</span>inFunctionLabel<span class="p">&amp;</span>rsquo<span class="p">;</span> used but not defined</code></pre></div> <p>So goto is at least bound to its scope.</p> Java Puzzle #1: Pre- and Postincrement //martin-thoma.com/java-puzzle-1-pre-and-postincrement/ Wed, 11 Jul 2012 16:07:02 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/java-puzzle-1-pre-and-postincrement <h2>The puzzle</h2> <p>What is the output of the following piece of code?</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">i</span> <span class="o">+=</span> <span class="o">++</span><span class="n">i</span> <span class="o">+</span> <span class="n">i</span><span class="o">++</span> <span class="o">+</span> <span class="o">++</span><span class="n">i</span><span class="o">;</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">j</span> <span class="o">+=</span> <span class="o">++</span><span class="n">j</span> <span class="o">+</span> <span class="n">j</span><span class="o">++</span> <span class="o">+</span> <span class="o">++</span><span class="n">j</span><span class="o">;</span> <span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">k</span> <span class="o">+=</span> <span class="n">k</span><span class="o">++</span> <span class="o">+</span> <span class="n">k</span><span class="o">++</span> <span class="o">+</span> <span class="o">++</span><span class="n">k</span><span class="o">;</span> <span class="kt">int</span> <span class="n">m</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;i = &quot;</span> <span class="o">+</span> <span class="n">i</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;j = &quot;</span> <span class="o">+</span> <span class="n">j</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;k = &quot;</span> <span class="o">+</span> <span class="n">k</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;m = &quot;</span> <span class="o">+</span> <span class="o">(</span><span class="n">m</span> <span class="o">+=</span> <span class="mi">1</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <p>The output is:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">i</span> <span class="o">=</span> 9 <span class="nv">j</span> <span class="o">=</span> 9 <span class="nv">k</span> <span class="o">=</span> 8 <span class="nv">m</span> <span class="o">=</span> 2</code></pre></div> <h2>Explanation</h2> <h3>Part one</h3> <p>First, take a look at statements of this structure:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">i</span> <span class="o">+=</span> <span class="n">s</span></code></pre></div> <p>where <code>i</code> is the integer and s is a statement (e.g. <code>++i</code>). This gets evaluated to</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">i</span> <span class="o">=</span> <span class="n">a</span> <span class="o">+</span> <span class="n">s</span></code></pre></div> <p>Source: <a href="http://wordpress.org/extend/plugins/embed-github-gist/">docs.oracle.com</a></p> <h3>Part two</h3> <p>Lets take a look at pre- and postincrement in Java.</p> <p>You can quite easily figure out what the different increments do by this snippet:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;i = &quot;</span> <span class="o">+</span> <span class="o">++</span><span class="n">i</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;i = &quot;</span> <span class="o">+</span> <span class="n">i</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;j = &quot;</span> <span class="o">+</span> <span class="n">j</span><span class="o">++);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;j = &quot;</span> <span class="o">+</span> <span class="n">j</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;k = &quot;</span> <span class="o">+</span> <span class="o">(</span><span class="n">k</span> <span class="o">+=</span> <span class="mi">1</span><span class="o">));</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">i</span> <span class="o">=</span> 1 <span class="nv">i</span> <span class="o">=</span> 1 <span class="nv">j</span> <span class="o">=</span> 0 <span class="nv">j</span> <span class="o">=</span> 1 <span class="nv">k</span> <span class="o">=</span> 1</code></pre></div> <p>Line 7 adds +1 to <code>i</code> and returns the value. Line 10 returns the value of <code>j</code> and adds +1 to <code>j</code>. Line 13 adds +1 to <code>k</code> and returns <code>k</code>.</p> <p>Lets return to the original puzzle. Java parses your code from left to right (<a href="http://docs.oracle.com/javase/tutorial/java/nutsandbolts/operators.html">Source 1</a>, <a href="http://docs.oracle.com/javase/specs/jls/se7/html/jls-15.html#jls-15.1">Source 2</a>).</p> <p>Most important:</p> <blockquote>Evaluation of an expression can also produce side effects, because expressions may contain embedded assignments, increment operators, decrement operators, and method invocations.</blockquote> <p>So:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">i</span> <span class="o">+=</span> <span class="o">++</span><span class="n">i</span> <span class="o">+</span> <span class="n">i</span><span class="o">++</span> <span class="o">+</span> <span class="o">++</span><span class="n">i</span><span class="o">;</span></code></pre></div> <p>is the same as</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">i</span> <span class="o">=</span> <span class="o">((</span><span class="n">i</span> <span class="o">+</span> <span class="o">(++</span><span class="n">i</span><span class="o">))</span> <span class="o">+</span> <span class="o">(</span><span class="n">i</span><span class="o">++))</span> <span class="o">+</span> <span class="o">(++</span><span class="n">i</span><span class="o">);</span></code></pre></div> <p>The first <code>++i</code> increments <code>i</code> to 2 and returns 2. So you have:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">i</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">i</span> <span class="o">=</span> <span class="o">((</span><span class="mi">1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">)</span> <span class="o">+</span> <span class="o">(</span><span class="n">i</span><span class="o">++))</span> <span class="o">+</span> <span class="o">(++</span><span class="n">i</span><span class="o">);</span></code></pre></div> <p>The <code>i++</code> returns 2, as it is the new value of <code>i</code>, and increments <code>i</code> to 3:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">i</span> <span class="o">=</span> <span class="mi">3</span><span class="o">;</span> <span class="n">i</span> <span class="o">=</span> <span class="o">((</span><span class="mi">1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">)</span> <span class="o">+</span> <span class="mi">2</span><span class="o">)</span> <span class="o">+</span> <span class="o">++</span><span class="n">i</span><span class="o">;</span></code></pre></div> <p>The second <code>++i</code> increments <code>i</code> to 4 and returns 4:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">i</span> <span class="o">=</span> <span class="mi">4</span><span class="o">;</span> <span class="n">i</span> <span class="o">+=</span> <span class="o">((</span><span class="mi">1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">)</span> <span class="o">+</span> <span class="mi">2</span><span class="o">)</span> <span class="o">+</span> <span class="mi">4</span><span class="o">;</span></code></pre></div> <p>So you end up with <code>9</code>.</p> <p>A <a href="http://en.wikipedia.org/wiki/Parse_tree">parse tree</a> of this evaluation would look like this:</p> <div style="width: 464px" class="wp-caption aligncenter"><a href="../images/2012/07/evaluation-tree.gif"><img src="../images/2012/07/evaluation-tree.gif" alt="Parse tree" width="" height="" class="size-full wp-image-30711" /></a><p class="wp-caption-text">Parse tree</p></div> <p>The explanation for the other three ones is similar.</p> <h2>See also</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Increment_and_decrement_operators">Increment and decrement operators</a></li> <li><a href="http://stackoverflow.com/q/971312/562769">Why avoid increment (&ldquo;++&rdquo;) and decrement (&ldquo;--&rdquo;) operators in JavaScript?</a></li> <li><a href="http://stackoverflow.com/q/11431914/562769">Pre- and postincrement in Java</a></li> </ul> What is a fractal? //martin-thoma.com/what-is-a-fractal/ Sat, 07 Jul 2012 19:00:09 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-is-a-fractal <blockquote>[...] Fractals are typically self-similar patterns, where self-similar means they are "the same from near as from far". [...] The definition of fractal goes beyond self-similarity per se to exclude trivial self-similarity and include the idea of a detailed pattern repeating itself.</blockquote> <p>Source: <a href="http://en.wikipedia.org/wiki/Fractal">Fractal</a>, Wikipedia</p> <h2>Examples</h2> <p>The <a href="http://en.wikipedia.org/wiki/Rensselaer_Polytechnic_Institute">Rensselaer Polytechnic Institute</a> made an <a href="http://www.ccd.rpi.edu/eglash/temp/CS%20RPI/Chapter%201.2.html">applet</a> which allows you to create fractals by yourself. So I’ve tried this one as a starter:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/martin-fractal-1-300x57.png"><img src="../images/2012/07/martin-fractal-1-300x57.png" alt="Martin Fractal #1" width="" height="" class="size-medium wp-image-29991" /></a><p class="wp-caption-text">Martin Fractal #1</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/martin-fractal-2-300x63.png"><img src="../images/2012/07/martin-fractal-2-300x63.png" alt="Martin Fractal #2" width="" height="" class="size-medium wp-image-30001" /></a><p class="wp-caption-text">Martin Fractal #2</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/martin-fractal-3-300x65.png"><img src="../images/2012/07/martin-fractal-3-300x65.png" alt="Martin Fractal #3" width="" height="" class="size-medium wp-image-30011" /></a><p class="wp-caption-text">Martin Fractal #3</p></div> <p>You might know this one:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/schnee-fractal-1-300x71.png"><img src="../images/2012/07/schnee-fractal-1-300x71.png" alt="Snowflake fractal #1" width="" height="" class="size-medium wp-image-30031" /></a><p class="wp-caption-text">Snowflake fractal #1</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/schnee-fractal-2-300x72.png"><img src="../images/2012/07/schnee-fractal-2-300x72.png" alt="Snowflake fractal #2" width="" height="" class="size-medium wp-image-30041" /></a><p class="wp-caption-text">Snowflake fractal #2</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/schnee-fractal-3-300x71.png"><img src="../images/2012/07/schnee-fractal-3-300x71.png" alt="Snowflake fractal #3" width="" height="" class="size-medium wp-image-30051" /></a><p class="wp-caption-text">Snowflake fractal #3</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/schnee-fractal-4-300x72.png"><img src="../images/2012/07/schnee-fractal-4-300x72.png" alt="Snowflake fractal #4" width="" height="" class="size-medium wp-image-30061" /></a><p class="wp-caption-text">Snowflake fractal #4</p></div> <h2>Fractals in Nature</h2> <p>Fractals seem to appear quite often in nature. I have just re-created one that I have seen recently:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractal-1-300x163.png"><img src="../images/2012/07/leaf-fractal-1-300x163.png" alt="Leaf fractal #1" width="" height="" class="size-medium wp-image-30081" /></a><p class="wp-caption-text">Leaf fractal #1</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractal-2-300x162.png"><img src="../images/2012/07/leaf-fractal-2-300x162.png" alt="Leaf fractal #2" width="" height="" class="size-medium wp-image-30091" /></a><p class="wp-caption-text">Leaf fractal #2</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractal-3-300x165.png"><img src="../images/2012/07/leaf-fractal-3-300x165.png" alt="Leaf fractal #3" width="" height="" class="size-medium wp-image-30101" /></a><p class="wp-caption-text">Leaf fractal #3</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractal-4-300x156.png"><img src="../images/2012/07/leaf-fractal-4-300x156.png" alt="Leaf fractal #4" width="" height="" class="size-medium wp-image-30111" /></a><p class="wp-caption-text">Leaf fractal #4</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractals-5-300x147.png"><img src="../images/2012/07/leaf-fractals-5-300x147.png" alt="Leaf fractal #5" width="" height="" class="size-medium wp-image-30121" /></a><p class="wp-caption-text">Leaf fractal #5</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractals-6-300x157.png"><img src="../images/2012/07/leaf-fractals-6-300x157.png" alt="Leaf fractal #6" width="" height="" class="size-medium wp-image-30131" /></a><p class="wp-caption-text">Leaf fractal #6</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/07/leaf-fractals-9-300x155.png"><img src="../images/2012/07/leaf-fractals-9-300x155.png" alt="Leaf fractal #9" width="" height="" class="size-medium wp-image-30141" /></a><p class="wp-caption-text">Leaf fractal #9</p></div> <h2>Mandelbrot set</h2> <p>The <a href="http://en.wikipedia.org/wiki/Mandelbrot_set">Mandelbrot set</a> is maybe the best known fractal, although it is not a fractal in my opinion. It does never repeat itself.</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/1o5FMTHkLQg" frameborder="0" allowfullscreen=""></iframe> <h2>See also</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Fractal">Fractal</a></li> <li>Mandelbrot set</li> <li><a href="http://www.acm.uiuc.edu/~troys2/tutorials/FractalTreeReel2.swf">Visualization of a fractal</a></li> <li>TED Talk: <a href="http://www.ted.com/talks/lang/en/ron_eglash_on_african_fractals.html">Ron Eglash on African fractals</a></li> </ul> My LaTeX Tikz Template //martin-thoma.com/my-latex-tikz-template/ Sat, 07 Jul 2012 17:38:13 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/my-latex-tikz-template <p>Sometimes I would like to create a single picture with Tikz for later usage on Wikipedia or my Blog. This is my LaTeX Tikz template I use in such a situation:</p> <h2>The templates</h2> <h3>latex-document.tex</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[varwidth=true, border=2pt]{standalone} \usepackage{tikz} \usetikzlibrary{arrows,positioning} \begin{document} \begin{tikzpicture} % Your Codes should be here \end{tikzpicture} \end{document} </pre></div> </div> </div> <h4>Standalone</h4> <h4>Preview-Environment</h4> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{article} \usepackage[pdftex,active,tightpage]{preview} \setlength\PreviewBorder{2mm} \usepackage{tikz} \usetikzlibrary{arrows,positioning} \begin{document} \begin{preview} \begin{tikzpicture} % Your Codes should be here \end{tikzpicture} \end{preview} \end{document} </pre></div> </div> </div> <h3>Makefile</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>SOURCE = latex-document.tex DELAY = 80 DENSITY = 300 make: pdflatex $(SOURCE).tex -output-format=pdf make clean clean: rm -rf $(TARGET) *.class *.html *.log *.aux animatedGif: pdfcrop $(SOURCE).pdf convert -verbose -delay $(DELAY) -loop 0 -density $(DENSITY) $(SOURCE)-crop.pdf $(SOURCE).gif make clean transparentGif: convert $(SOURCE).pdf -transparent white result.gif make clean svg: pdf2svg $(SOURCE).pdf $(SOURCE).svg # Necessary, as pdf2svg does not always create valid svgs: inkscape $(SOURCE).svg --export-plain-svg=$(SOURCE).svg # Alternatively, only this one (produces worse results): #inkscape $(SOURCE).pdf --export-plain-svg=$(SOURCE).svg </pre></div> </div> </div> <h2>Requirements</h2> <ul> <li>LaTeX (<a href="../how-to-install-the-latest-latex-version/" title="How to install the latest LaTeX Version">How to install the latest LaTeX Version</a>)</li> <li>make</li> <li>Inkscape</li> <li>pdf2svg</li> </ul> <h2>Test if you meet these requirements</h2> <p>Make sure that you have a valid LaTeX installation. <code>pdflatex --version</code> should output something like:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pdfTeX 3.1415926-2.3-1.40.12 (TeX Live 2011) kpathsea version 6.0.1 Copyright 2011 Peter Breitenlohner (eTeX)/Han The Thanh (pdfTeX). There is NO warranty. Redistribution of this software is covered by the terms of both the pdfTeX copyright and the Lesser GNU General Public License. For more information about these matters, see the file named COPYING and the pdfTeX source. Primary author of pdfTeX: Peter Breitenlohner (eTeX)/Han The Thanh (pdfTeX). Compiled with libpng 1.5.2; using libpng 1.5.2 Compiled with zlib 1.2.5; using zlib 1.2.5 Compiled with xpdf version 3.02pl5 </pre></div> </div> </div> <p>Make sure you can execute Makefiles. <code>make --version</code> should output something like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>GNU Make 3.81 Copyright (C) 2006 Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. This program built for i486-pc-linux-gnu </pre></div> </div> </div> <p>The command <code>inkscape --version</code> should return:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Inkscape 0.47 r22583 <span class="o">(</span>Apr <span class="m">4</span> 2010<span class="o">)</span></code></pre></div> <p>And <code>pdf2svg --version</code> should return:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Usage: pdf2svg &lt;in file.pdf&gt; &lt;out file.svg&gt; <span class="o">[</span>&lt;page no&gt;<span class="o">]</span></code></pre></div> <h2>How to use it</h2> <p>You have to place the Makefile in the same folder as latex-document.tex. If you have done this and if you meet the requirements, you can execute:</p> <ul> <li><code>make</code>: Generates a PDF file from latex-document.tex</li> <li><code>make svg</code>: Generates a SVG file from the generated PDF file</li> <li><code>make transparentGif</code>: Generates a transparent Gif from the PDF file</li> <li><code>make animatedGif</code>: If you have used multiple slides, this will create an animated Gif file. See <a href="../how-to-visualize-graph-algorithms-with-latex/" title="How to visualize Graph algorithms with LaTeX">How to visualize Graph algorithms with LaTeX</a> for an example.</li> </ul> <h2>See also</h2> <ul> <li><a href="../how-to-print-source-code-with-latex/" title="How to print Source Code with LaTeX">How to print Source Code with LaTeX</a></li> <li><a href="../briefe-mit-latex-schreiben/" title="Briefe mit LaTeX schreiben">Briefe mit LaTeX schreiben</a> (A template for letters)</li> <li><a href="../plotting-function-graphs-with-latex/" title="Plotting function graphs with LaTeX">Plotting function graphs with LaTeX</a></li> </ul> C++ Operator overloading //martin-thoma.com/cpp-operator-overloading/ Fri, 06 Jul 2012 16:00:22 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cpp-operator-overloading <p>Operator overloading is heavily used in math. One of the most famous examples I know is “+”. If you add two elements from <code>$\mathbb{N}$</code> you will use the same character “+” as you use for adding two numbers from <code>$\mathbb{R}$</code>. You even use the plus-sign if you add matrices (which is obviously something different than adding single numbers).</p> <p>In some programming languages, like C++, you can overload operators by yourself.</p> <h2>First simple example</h2> <p>Imagine you wanted to store some data - lets say the prename, surname and age - about people you know. This could be done in a <code>struct</code>. After you’ve stored it, you would like to print this information. Obviously, you don’t want to do something like this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Person(&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">prename</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">surname</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;, &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">age</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;)&quot;</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>If you wanted to print this information more than one time, you would have to add this long line every time.</p> <p>A <a href="http://docs.oracle.com/javase/6/docs/api/java/lang/Object.html#toString()">toString()</a> method like the one Java uses would be nice. In C++, you don’t have toString, but you can overload the <code>&lt;&lt;</code> operator!</p> <p>This is how it works:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">typedef</span> <span class="k">struct</span> <span class="n">person</span> <span class="p">{</span> <span class="c1">// attributes</span> <span class="n">string</span> <span class="n">prename</span><span class="p">;</span> <span class="n">string</span> <span class="n">surname</span><span class="p">;</span> <span class="kt">int</span> <span class="n">age</span><span class="p">;</span> <span class="c1">// constructor</span> <span class="n">person</span><span class="p">(</span><span class="n">string</span> <span class="n">p</span><span class="p">,</span> <span class="n">string</span> <span class="n">s</span><span class="p">,</span> <span class="kt">int</span> <span class="n">age</span><span class="p">)</span> <span class="o">:</span> <span class="n">prename</span><span class="p">(</span><span class="n">p</span><span class="p">),</span> <span class="n">surname</span><span class="p">(</span><span class="n">s</span><span class="p">),</span> <span class="n">age</span><span class="p">(</span><span class="n">age</span><span class="p">)</span> <span class="p">{}</span> <span class="p">}</span> <span class="n">Person</span><span class="p">;</span> <span class="c1">// &quot;toString&quot; for C++</span> <span class="n">std</span><span class="o">::</span><span class="n">ostream</span><span class="o">&amp;</span> <span class="k">operator</span><span class="o">&lt;&lt;</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">ostream</span> <span class="o">&amp;</span><span class="n">strm</span><span class="p">,</span> <span class="k">const</span> <span class="n">person</span> <span class="o">&amp;</span><span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">strm</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Person(&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">prename</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">surname</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;, &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">age</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;)&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span><span class="p">(){</span> <span class="n">Person</span> <span class="n">Martin</span> <span class="p">(</span><span class="s">&quot;Martin&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">Andreas</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">AndiOld</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">30</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">AndiYoung</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="n">myArray</span><span class="p">[]</span> <span class="o">=</span> <span class="p">{</span><span class="n">Martin</span><span class="p">,</span> <span class="n">Andreas</span><span class="p">,</span> <span class="n">AndiOld</span><span class="p">,</span> <span class="n">AndiYoung</span><span class="p">};</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>Sorting</h2> <p>You can sort by overloading <code>&lt;</code>. You can use a sort by adding</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;algorithm&gt;</span></code></pre></div> <p>to your program and using <code>sort(array, array + elements);</code></p> <p>This is how it looks like:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;algorithm&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">typedef</span> <span class="k">struct</span> <span class="n">person</span> <span class="p">{</span> <span class="c1">// attributes</span> <span class="n">string</span> <span class="n">prename</span><span class="p">;</span> <span class="n">string</span> <span class="n">surname</span><span class="p">;</span> <span class="kt">int</span> <span class="n">age</span><span class="p">;</span> <span class="c1">// constructor</span> <span class="n">person</span><span class="p">(</span><span class="n">string</span> <span class="n">p</span><span class="p">,</span> <span class="n">string</span> <span class="n">s</span><span class="p">,</span> <span class="kt">int</span> <span class="n">age</span><span class="p">)</span> <span class="o">:</span> <span class="n">prename</span><span class="p">(</span><span class="n">p</span><span class="p">),</span> <span class="n">surname</span><span class="p">(</span><span class="n">s</span><span class="p">),</span> <span class="n">age</span><span class="p">(</span><span class="n">age</span><span class="p">)</span> <span class="p">{}</span> <span class="p">}</span> <span class="n">Person</span><span class="p">;</span> <span class="c1">// &quot;.equals()&quot; for C++</span> <span class="kt">bool</span> <span class="k">operator</span><span class="o">&lt;</span><span class="p">(</span><span class="k">const</span> <span class="n">Person</span><span class="o">&amp;</span> <span class="n">a</span><span class="p">,</span> <span class="k">const</span> <span class="n">Person</span><span class="o">&amp;</span> <span class="n">b</span><span class="p">){</span> <span class="k">if</span> <span class="p">(</span><span class="o">!</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">prename</span> <span class="o">==</span> <span class="n">b</span><span class="p">.</span><span class="n">prename</span><span class="p">))</span> <span class="p">{</span> <span class="k">return</span> <span class="n">a</span><span class="p">.</span><span class="n">prename</span> <span class="o">&lt;</span> <span class="n">b</span><span class="p">.</span><span class="n">prename</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="k">if</span> <span class="p">(</span><span class="o">!</span><span class="p">(</span><span class="n">a</span><span class="p">.</span><span class="n">surname</span> <span class="o">&lt;</span> <span class="n">b</span><span class="p">.</span><span class="n">surname</span><span class="p">))</span> <span class="p">{</span> <span class="k">return</span> <span class="n">a</span><span class="p">.</span><span class="n">surname</span> <span class="o">&lt;</span> <span class="n">b</span><span class="p">.</span><span class="n">surname</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="k">return</span> <span class="n">a</span><span class="p">.</span><span class="n">age</span> <span class="o">&lt;</span> <span class="n">b</span><span class="p">.</span><span class="n">age</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="c1">// &quot;toString&quot; for C++</span> <span class="n">std</span><span class="o">::</span><span class="n">ostream</span><span class="o">&amp;</span> <span class="k">operator</span><span class="o">&lt;&lt;</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="n">ostream</span> <span class="o">&amp;</span><span class="n">strm</span><span class="p">,</span> <span class="k">const</span> <span class="n">person</span> <span class="o">&amp;</span><span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">strm</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Person(&quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">prename</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">surname</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;, &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">a</span><span class="p">.</span><span class="n">age</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;)&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span><span class="p">(){</span> <span class="n">Person</span> <span class="n">Martin</span> <span class="p">(</span><span class="s">&quot;Martin&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">Andreas</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">AndiOld</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">30</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">AndiYoung</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="n">myArray</span><span class="p">[]</span> <span class="o">=</span> <span class="p">{</span><span class="n">Martin</span><span class="p">,</span> <span class="n">Andreas</span><span class="p">,</span> <span class="n">AndiOld</span><span class="p">,</span> <span class="n">AndiYoung</span><span class="p">};</span> <span class="n">sort</span><span class="p">(</span><span class="n">myArray</span><span class="p">,</span> <span class="n">myArray</span> <span class="o">+</span> <span class="mi">4</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>By the way, if you don’t define <code>&lt;</code> you get something like this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">In</span> <span class="n">file</span> <span class="n">included</span> <span class="n">from</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="nl">algorithm</span><span class="p">:</span><span class="mi">62</span><span class="p">,</span> <span class="n">from</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">2</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">const</span> <span class="n">_Tp</span><span class="o">&amp;</span> <span class="n">std</span><span class="o">::</span><span class="n">__median</span><span class="p">(</span><span class="k">const</span> <span class="n">_Tp</span><span class="o">&amp;</span><span class="p">,</span> <span class="k">const</span> <span class="n">_Tp</span><span class="o">&amp;</span><span class="p">,</span> <span class="k">const</span> <span class="n">_Tp</span><span class="o">&amp;</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_Tp</span> <span class="o">=</span> <span class="n">person</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2268</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__introsort_loop</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Size</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Size</span> <span class="o">=</span> <span class="kt">int</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5220</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">89</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__a</span> <span class="o">&lt;</span> <span class="n">__b</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">90</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__b</span> <span class="o">&lt;</span> <span class="n">__c</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">92</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__a</span> <span class="o">&lt;</span> <span class="n">__c</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">96</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__a</span> <span class="o">&lt;</span> <span class="n">__c</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">98</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__b</span> <span class="o">&lt;</span> <span class="n">__c</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">_RandomAccessIterator</span> <span class="n">std</span><span class="o">::</span><span class="n">__unguarded_partition</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Tp</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Tp</span> <span class="o">=</span> <span class="n">person</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2268</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__introsort_loop</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Size</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Size</span> <span class="o">=</span> <span class="kt">int</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5220</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2209</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="o">*</span> <span class="n">__first</span> <span class="o">&lt;</span> <span class="n">__pivot</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2212</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__pivot</span> <span class="o">&lt;</span> <span class="o">*</span> <span class="n">__last</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__insertion_sort</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2178</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__final_insertion_sort</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5222</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2106</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__val</span> <span class="o">&lt;</span> <span class="o">*</span> <span class="n">__first</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__heap_select</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5067</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">partial_sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2256</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__introsort_loop</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Size</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Size</span> <span class="o">=</span> <span class="kt">int</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5220</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">1906</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="o">*</span> <span class="n">__i</span> <span class="o">&lt;</span> <span class="o">*</span> <span class="n">__first</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__unguarded_linear_insert</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Tp</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Tp</span> <span class="o">=</span> <span class="n">person</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2112</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__insertion_sort</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2178</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__final_insertion_sort</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5222</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2067</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="n">__val</span> <span class="o">&lt;</span> <span class="o">*</span> <span class="n">__next</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">In</span> <span class="n">file</span> <span class="n">included</span> <span class="n">from</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">62</span><span class="p">,</span> <span class="n">from</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="nl">algorithm</span><span class="p">:</span><span class="mi">62</span><span class="p">,</span> <span class="n">from</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">2</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__adjust_heap</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Distance</span><span class="p">,</span> <span class="n">_Distance</span><span class="p">,</span> <span class="n">_Tp</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Distance</span> <span class="o">=</span> <span class="kt">int</span><span class="p">,</span> <span class="n">_Tp</span> <span class="o">=</span> <span class="n">person</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">394</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">make_heap</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">1904</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__heap_select</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5067</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">partial_sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2256</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__introsort_loop</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Size</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Size</span> <span class="o">=</span> <span class="kt">int</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5220</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">232</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="o">*</span><span class="p">(</span><span class="n">__first</span> <span class="o">+</span> <span class="p">((</span><span class="kt">unsigned</span> <span class="kt">int</span><span class="p">)(((</span><span class="kt">unsigned</span> <span class="kt">int</span><span class="p">)</span><span class="n">__secondChild</span><span class="p">)</span> <span class="o">*</span> <span class="mi">12u</span><span class="p">)))</span> <span class="o">&lt;</span> <span class="o">*</span><span class="p">(</span><span class="n">__first</span> <span class="o">+</span> <span class="p">((((</span><span class="kt">unsigned</span> <span class="kt">int</span><span class="p">)</span><span class="n">__secondChild</span><span class="p">)</span> <span class="o">+</span> <span class="mh">0xffffffffffffffffffffffffffffffffu</span><span class="p">)</span> <span class="o">*</span> <span class="mi">12u</span><span class="p">))</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span> <span class="n">In</span> <span class="n">function</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__push_heap</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Distance</span><span class="p">,</span> <span class="n">_Distance</span><span class="p">,</span> <span class="n">_Tp</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Distance</span> <span class="o">=</span> <span class="kt">int</span><span class="p">,</span> <span class="n">_Tp</span> <span class="o">=</span> <span class="n">person</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span><span class="o">:</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">244</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__adjust_heap</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Distance</span><span class="p">,</span> <span class="n">_Distance</span><span class="p">,</span> <span class="n">_Tp</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Distance</span> <span class="o">=</span> <span class="kt">int</span><span class="p">,</span> <span class="n">_Tp</span> <span class="o">=</span> <span class="n">person</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">394</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">make_heap</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">1904</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__heap_select</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5067</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">partial_sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">2256</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">__introsort_loop</span><span class="p">(</span><span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_RandomAccessIterator</span><span class="p">,</span> <span class="n">_Size</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RandomAccessIterator</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">,</span> <span class="n">_Size</span> <span class="o">=</span> <span class="kt">int</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_algo</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">5220</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">void</span> <span class="n">std</span><span class="o">::</span><span class="n">sort</span><span class="p">(</span><span class="n">_RAIter</span><span class="p">,</span> <span class="n">_RAIter</span><span class="p">)</span> <span class="p">[</span><span class="n">with</span> <span class="n">_RAIter</span> <span class="o">=</span> <span class="n">Person</span><span class="o">*</span><span class="p">]</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">34</span><span class="o">:</span> <span class="n">instantiated</span> <span class="n">from</span> <span class="n">here</span> <span class="o">/</span><span class="n">usr</span><span class="o">/</span><span class="n">include</span><span class="o">/</span><span class="n">c</span><span class="o">++/</span><span class="mf">4.4</span><span class="o">/</span><span class="n">bits</span><span class="o">/</span><span class="n">stl_heap</span><span class="p">.</span><span class="nl">h</span><span class="p">:</span><span class="mi">134</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">no</span> <span class="n">match</span> <span class="k">for</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="k">operator</span><span class="o">&lt;&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="o">*</span><span class="p">(</span><span class="n">__first</span> <span class="o">+</span> <span class="p">((</span><span class="kt">unsigned</span> <span class="kt">int</span><span class="p">)(((</span><span class="kt">unsigned</span> <span class="kt">int</span><span class="p">)</span><span class="n">__parent</span><span class="p">)</span> <span class="o">*</span> <span class="mi">12u</span><span class="p">)))</span> <span class="o">&lt;</span> <span class="n">__value</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span></code></pre></div> <h2>Equality</h2> <p>You can also define <code>==</code> for your structs.</p> <p>I know this example does NOT make any sense. But it is an example you can work with:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">typedef</span> <span class="k">struct</span> <span class="n">person</span> <span class="p">{</span> <span class="c1">// attributes</span> <span class="n">string</span> <span class="n">prename</span><span class="p">;</span> <span class="n">string</span> <span class="n">surname</span><span class="p">;</span> <span class="kt">int</span> <span class="n">age</span><span class="p">;</span> <span class="c1">// constructor</span> <span class="n">person</span><span class="p">(</span><span class="n">string</span> <span class="n">p</span><span class="p">,</span> <span class="n">string</span> <span class="n">s</span><span class="p">,</span> <span class="kt">int</span> <span class="n">age</span><span class="p">)</span> <span class="o">:</span> <span class="n">prename</span><span class="p">(</span><span class="n">p</span><span class="p">),</span> <span class="n">surname</span><span class="p">(</span><span class="n">s</span><span class="p">),</span> <span class="n">age</span><span class="p">(</span><span class="n">age</span><span class="p">)</span> <span class="p">{}</span> <span class="p">}</span> <span class="n">Person</span><span class="p">;</span> <span class="c1">// &quot;comperator&quot; for C++</span> <span class="kt">bool</span> <span class="k">operator</span><span class="o">==</span><span class="p">(</span><span class="k">const</span> <span class="n">Person</span><span class="o">&amp;</span> <span class="n">a</span><span class="p">,</span> <span class="k">const</span> <span class="n">Person</span><span class="o">&amp;</span> <span class="n">b</span><span class="p">){</span> <span class="k">return</span> <span class="n">a</span><span class="p">.</span><span class="n">age</span> <span class="o">==</span> <span class="mi">30</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span><span class="p">(){</span> <span class="n">Person</span> <span class="n">Martin</span> <span class="p">(</span><span class="s">&quot;Martin&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">Andreas</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">AndiOld</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">30</span><span class="p">);</span> <span class="n">Person</span> <span class="nf">AndiYoung</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="n">myArray</span><span class="p">[]</span> <span class="o">=</span> <span class="p">{</span><span class="n">Martin</span><span class="p">,</span> <span class="n">Andreas</span><span class="p">,</span> <span class="n">AndiOld</span><span class="p">,</span> <span class="n">AndiYoung</span><span class="p">};</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">==</span> <span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>Casting</h2> <p>You can also define casts:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">typedef</span> <span class="k">struct</span> <span class="n">person</span> <span class="p">{</span> <span class="c1">// attributes</span> <span class="n">string</span> <span class="n">prename</span><span class="p">;</span> <span class="n">string</span> <span class="n">surname</span><span class="p">;</span> <span class="kt">int</span> <span class="n">age</span><span class="p">;</span> <span class="c1">// constructor</span> <span class="n">person</span><span class="p">(</span><span class="n">string</span> <span class="n">p</span><span class="p">,</span> <span class="n">string</span> <span class="n">s</span><span class="p">,</span> <span class="kt">int</span> <span class="n">age</span><span class="p">)</span> <span class="o">:</span> <span class="n">prename</span><span class="p">(</span><span class="n">p</span><span class="p">),</span> <span class="n">surname</span><span class="p">(</span><span class="n">s</span><span class="p">),</span> <span class="n">age</span><span class="p">(</span><span class="n">age</span><span class="p">)</span> <span class="p">{}</span> <span class="c1">// prefix</span> <span class="k">operator</span> <span class="kt">int</span><span class="p">()</span> <span class="p">{</span> <span class="k">return</span> <span class="n">age</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">Person</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(){</span> <span class="n">Person</span> <span class="n">Martin</span> <span class="p">(</span><span class="s">&quot;Martin&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="n">Andreas</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Thoma&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="n">AndiOld</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">30</span><span class="p">);</span> <span class="n">Person</span> <span class="n">AndiYoung</span> <span class="p">(</span><span class="s">&quot;Andreas&quot;</span><span class="p">,</span> <span class="s">&quot;Berger&quot;</span><span class="p">,</span> <span class="mi">22</span><span class="p">);</span> <span class="n">Person</span> <span class="n">myArray</span><span class="p">[]</span> <span class="o">=</span> <span class="p">{</span><span class="n">Martin</span><span class="p">,</span> <span class="n">Andreas</span><span class="p">,</span> <span class="n">AndiOld</span><span class="p">,</span> <span class="n">AndiYoung</span><span class="p">};</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span> <span class="mi">4</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="kt">int</span><span class="p">(</span><span class="n">myArray</span><span class="p">[</span><span class="n">i</span><span class="p">])</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>Adding new operators</h2> <p>I like Python very much. Python allows me to get the power of a number like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">a</span> <span class="o">=</span> <span class="mi">2</span><span class="o">**</span><span class="mi">10</span> <span class="c"># 1024</span></code></pre></div> <p>Lets try it for C++:</p> <h3>Doesn't work</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="c1">// does NOT work</span> <span class="c1">// operators.cpp:7: error: expected initializer before &amp;lsquo;*&amp;rsquo; token</span> <span class="kt">int</span> <span class="k">operator</span><span class="o">**</span><span class="p">(</span><span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="kt">int</span> <span class="n">b</span><span class="p">){</span> <span class="kt">int</span> <span class="n">power</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">b</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">power</span> <span class="o">*=</span> <span class="n">a</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">power</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span><span class="p">(){</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="mi">2</span><span class="o">**</span><span class="mi">10</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>I guess it doesn’t work as it would be very difficult to distinguish something like this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">a</span> <span class="o">=</span> <span class="n">a</span> <span class="o">*</span> <span class="o">*</span><span class="n">b</span><span class="p">;</span> <span class="n">a</span> <span class="o">=</span> <span class="n">a</span> <span class="o">**</span> <span class="n">b</span><span class="p">;</span></code></pre></div> <p>If you try to use a <code>`$</code> you get:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">16</span><span class="o">:</span><span class="mi">13</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">invalid</span> <span class="n">suffix</span> <span class="s">&quot;$`10&quot;</span> <span class="n">on</span> <span class="n">integer</span> <span class="n">constant</span></code></pre></div> <p>If you try to use a <code>&sect;</code> you get:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">7</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">stray</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="err">\</span><span class="mi">302</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="n">program</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">7</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">stray</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="err">\</span><span class="mi">247</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="n">program</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">16</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">stray</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="err">\</span><span class="mi">302</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="n">program</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">16</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">stray</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="err">\</span><span class="mi">247</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">in</span> <span class="n">program</span> <span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">7</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="n">expected</span> <span class="n">type</span><span class="o">-</span><span class="n">specifier</span> <span class="n">before</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;(</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">token</span></code></pre></div> <p>You are also not allowed to redefine <code>*</code>:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">operators</span><span class="p">.</span><span class="nl">cpp</span><span class="p">:</span><span class="mi">7</span><span class="o">:</span> <span class="nl">error</span><span class="p">:</span> <span class="o">&amp;</span><span class="n">lsquo</span><span class="p">;</span><span class="kt">int</span> <span class="k">operator</span><span class="o">*</span><span class="p">(</span><span class="kt">int</span><span class="p">,</span> <span class="kt">int</span><span class="p">)</span><span class="o">&amp;</span><span class="n">rsquo</span><span class="p">;</span> <span class="n">must</span> <span class="n">have</span> <span class="n">an</span> <span class="n">argument</span> <span class="n">of</span> <span class="k">class</span> <span class="nc">or</span> <span class="n">enumerated</span> <span class="n">type</span></code></pre></div> <h3>Works</h3> <p>You can wrap the integer like this:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">typedef</span> <span class="k">struct</span> <span class="n">integer</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">inner</span><span class="p">;</span> <span class="c1">// constructor</span> <span class="n">integer</span><span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="p">)</span> <span class="o">:</span> <span class="n">inner</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="p">{}</span> <span class="p">}</span> <span class="n">Integer</span><span class="p">;</span> <span class="kt">int</span> <span class="k">operator</span><span class="o">^</span><span class="p">(</span><span class="n">Integer</span> <span class="n">a</span><span class="p">,</span> <span class="n">Integer</span> <span class="n">b</span><span class="p">){</span> <span class="kt">int</span> <span class="n">power</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">b</span><span class="p">.</span><span class="n">inner</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">power</span> <span class="o">*=</span> <span class="n">a</span><span class="p">.</span><span class="n">inner</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="n">power</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span><span class="p">(){</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="p">(</span><span class="n">Integer</span><span class="p">(</span><span class="mi">2</span><span class="p">)</span><span class="o">^</span><span class="n">Integer</span><span class="p">(</span><span class="mi">10</span><span class="p">))</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="c1">// outputs 1024</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>See also</h2> <ul> <li>A class for <a href="../fractions-in-cpp/">dealing with fractions</a> - which includes 7 examples for operator overloading</li> <li><a href="http://en.wikipedia.org/wiki/Operators_in_C_and_C%2B%2B">Operators in C and C++</a></li> <li><a href="http://stackoverflow.com/a/4421715/562769">The General Syntax of operator overloading in C++</a>. sbi, Stack Overflow.</li> <li><a href="http://stackoverflow.com/a/4421708/562769">The Three Basic Rules of Operator Overloading in C++</a>. sbi, Stack Overflow.</li> <li><a href="http://www.cplusplus.com/doc/tutorial/classes2/">Overloading operators</a>. C++-Reference.</li> </ul> Mathe Puzzle #1: Verschleierung //martin-thoma.com/mathe-puzzle-1-verschleierung/ Wed, 04 Jul 2012 20:54:42 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/mathe-puzzle-1-verschleierung <p><strong>Die folgende Funktion ist sehr bekannt. Wie lautet ihr Name?</strong></p> <p>Seien <code>$\oplus, \otimes: \mathbb{R} \times \mathbb{R} \rightarrow \mathbb{R}$</code> Verknüfungen auf <code>$\mathbb{R}$</code> und definiert durch: <code>$\oplus(a, b) := a + b$</code> <code>$\otimes(a, b) := a - b$</code></p> <p>Sei <code>$O:\mathbb{N} \rightarrow \mathbb{R}$</code> eine Abbildung und definiert durch <code>$O(0) := 0, O(0^0) := 0^0, O(o) := O(o \otimes 0^0) \oplus O(o \otimes 0^0 \otimes 0^0)$</code>.</p> <p>. . . . . . .</p> <p>Auflösung gibts weiter unten - die Abbildung ist wirklich sehr bekannt ☺</p> <p>. . . . . . . . . . . . . . . . . . . .</p> <p>Schreiben wir das doch mal um. Wenn wir schon die normale Addition bzw. Subtraktion des Körpers <code>$\mathbb{R}$</code> benutzen, können wir auch die gewohnten Symbole verwenden: <code>$O:\mathbb{N} \rightarrow \mathbb{R}$</code> <code>$O(0) := 0, O(0^0) := 0^0, O(o) := O(o - 0^0) + O(o - 0^0 - 0^0)$</code></p> <p>Nun sind wir es gewohnt, dass die Funktionen <code>$f$</code> heißen und die Variablen x: <code>$f:\mathbb{N} \rightarrow \mathbb{R}$</code> <code>$f(0) := 0, f(0^0) := 0^0, f(x) := f(x - 0^0) + f(x - 0^0 - 0^0)$</code></p> <p>Außerdem ist <code>$0^0 = 1$</code>: <code>$f:\mathbb{N} \rightarrow \mathbb{R}$</code> <code>$f(0) := 0, f(1) := 1, f(x) := f(x - 1) + f(x - 1 - 1)$</code></p> <p>Das ist wiederum: Außerdem ist <code>$0^0 = 1$</code>: <code>$f:\mathbb{N} \rightarrow \mathbb{R}$</code> <code>$f(0) := 0$</code>, <code>$f(1) := 1$</code>, <code>$f(x) := f(x - 1) + f(x - 2)$</code></p> <p>Diese Folge wird <a href="http://de.wikipedia.org/wiki/Fibonacci-Folge">Fibonacci-Folge</a> genannt. Es ist schon sehr erstaunlich, wie beeinflussbar wir von Symbolen und Konventionen sind.</p> <p>Und weil sie so schön sind, hier noch ein kurzes Video zu den Fibonacci-Zahlen:</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/kkGeOWYOFoA" frameborder="0" allowfullscreen=""></iframe> How to create your own Python module //martin-thoma.com/how-to-create-your-own-python-module/ Wed, 04 Jul 2012 16:11:54 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-create-your-own-python-module <p>A python module is a container for some definitions and statements. You generally call it like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">import</span> <span class="nn">math</span></code></pre></div> <p>or like that</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">ceil</span></code></pre></div> <p>or</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">import</span> <span class="nn">math</span> <span class="kn">as</span> <span class="nn">mymath</span></code></pre></div> <p>Python modules can also be written in C or C++, but I’ll only explain how to write the module in Python. Modules can be written in C++ for performance reasons. Just take a look at <code>/usr/lib/python3.1/lib-dynload</code> with all the *.so files (shared libraries).</p> <h2>Python Paths</h2> <p>When you try to import a module, Python looks at these directories in the given order:</p> <ul> <li>the PYTHONPATH</li> <li>the current working directory</li> <li>the default search path</li> </ul> <p>You get your PYTHONPATH and your default search path like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">import</span> <span class="nn">os</span> <span class="n">os</span><span class="o">.</span><span class="n">environ</span><span class="p">[</span><span class="s">&#39;PATH&#39;</span><span class="p">]</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">pathsep</span><span class="p">)</span> <span class="n">os</span><span class="o">.</span><span class="n">environ</span><span class="p">[</span><span class="s">&#39;PYTHONPATH&#39;</span><span class="p">]</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="n">os</span><span class="o">.</span><span class="n">pathsep</span><span class="p">)</span></code></pre></div> <h2>Example</h2> <p>I’ve just searched for a Python module for primes. It seems as if no such module existed. So I wrote the module <strong>primes.py</strong>.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="sd">&quot;&quot;&quot;</span> <span class="sd">This module offers some functions related to primes.</span> <span class="sd">&quot;&quot;&quot;</span> <span class="k">def</span> <span class="nf">miller_rabin</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="kn">import</span> <span class="nn">random</span> <span class="sd">&quot;&quot;&quot; Source: http://en.literateprograms.org/</span> <span class="sd"> Miller-Rabin_primality_test_(Python)</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="n">d</span> <span class="o">=</span> <span class="n">n</span> <span class="o">-</span> <span class="mi">1</span> <span class="n">s</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">while</span> <span class="n">d</span> <span class="o">%</span> <span class="mi">2</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">d</span> <span class="o">&gt;&gt;=</span> <span class="mi">1</span> <span class="n">s</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">repeat</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">20</span><span class="p">):</span> <span class="n">a</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">while</span> <span class="n">a</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">a</span> <span class="o">=</span> <span class="n">random</span><span class="o">.</span><span class="n">randrange</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">miller_rabin_pass</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">s</span><span class="p">,</span> <span class="n">d</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">def</span> <span class="nf">miller_rabin_pass</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">s</span><span class="p">,</span> <span class="n">d</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">a_to_power</span> <span class="o">=</span> <span class="nb">pow</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">d</span><span class="p">,</span> <span class="n">n</span><span class="p">)</span> <span class="k">if</span> <span class="n">a_to_power</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">s</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">a_to_power</span> <span class="o">==</span> <span class="n">n</span> <span class="o">-</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="bp">True</span> <span class="n">a_to_power</span> <span class="o">=</span> <span class="p">(</span><span class="n">a_to_power</span> <span class="o">*</span> <span class="n">a_to_power</span><span class="p">)</span> <span class="o">%</span> <span class="n">n</span> <span class="k">return</span> <span class="n">a_to_power</span> <span class="o">==</span> <span class="n">n</span> <span class="o">-</span> <span class="mi">1</span> <span class="k">def</span> <span class="nf">getPrimeFactors</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;Return the prime factors of n.</span> <span class="sd"> If the result is small enough to fit in an int, return an int.</span> <span class="sd"> Else return a long.</span> <span class="sd"> &gt;&gt;&gt; [getPrimeFactors(n) for n in range(11)]</span> <span class="sd"> [[], [], [2], [3], [2, 2], [5], [2, 3], [7], [2, 2, 2], [3, 3], [2, 5]]</span> <span class="sd"> &gt;&gt;&gt; getPrimeFactors(36)</span> <span class="sd"> [2, 2, 3, 3]</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="kn">import</span> <span class="nn">math</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">0</span><span class="p">:</span> <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&quot;n must be &gt;= 0&quot;</span><span class="p">)</span> <span class="k">if</span> <span class="n">math</span><span class="o">.</span><span class="n">floor</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="o">!=</span> <span class="n">n</span><span class="p">:</span> <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&quot;n must be exact integer&quot;</span><span class="p">)</span> <span class="k">elif</span> <span class="n">n</span> <span class="o">&lt;=</span> <span class="mi">2147483647</span><span class="p">:</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">long</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="n">fact</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="n">fact</span> <span class="k">while</span> <span class="n">n</span> <span class="o">%</span> <span class="mi">2</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">fact</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="mi">2</span><span class="p">)</span> <span class="n">n</span> <span class="o">/=</span> <span class="mi">2</span> <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="n">fact</span> <span class="k">if</span> <span class="n">miller_rabin</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">fact</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="k">return</span> <span class="n">fact</span> <span class="n">check</span> <span class="o">=</span> <span class="mi">3</span> <span class="n">rootn</span> <span class="o">=</span> <span class="n">n</span><span class="o">**</span><span class="mf">0.5</span> <span class="k">while</span> <span class="n">n</span> <span class="o">!=</span> <span class="mi">1</span><span class="p">:</span> <span class="k">while</span> <span class="n">n</span> <span class="o">%</span> <span class="n">check</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="n">fact</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">check</span><span class="p">)</span> <span class="n">n</span> <span class="o">/=</span> <span class="n">check</span> <span class="n">check</span><span class="o">+=</span><span class="mi">2</span> <span class="k">return</span> <span class="n">fact</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">doctest</span> <span class="n">doctest</span><span class="o">.</span><span class="n">testmod</span><span class="p">()</span></code></pre></div> <h2>See also</h2> <ul> <li><a href="http://docs.python.org/tutorial/modules.html">Modules</a></li> <li><a href="http://www.python-kurs.eu/modularisierung.php">Modularisierung</a> (German)</li> <li><a href="http://stackoverflow.com/q/7948494/562769">What's the difference between a Python module and a Python package?</a></li> <li>Packages: <ul> <li><a href="http://guide.python-distribute.org/creation.html">Creating a Package</a></li> <li><a href="http://docs.python.org/distutils/introduction.html">An Introduction to Distutils</a></li> </ul> </li> </ul> Wie berechnet man die Cholesky-Zerlegung? //martin-thoma.com/wie-berechnet-man-die-cholesky-zerlegung/ Tue, 03 Jul 2012 19:09:22 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-berechnet-man-die-cholesky-zerlegung <p>Sei <code>$A \in \mathbb{R}^{n \times n}$</code> eine symmetrische, positiv definite Matrix. Dann existiert eine Zerlegung <code>$A = S \cdot D \cdot S^T$</code>, wobei <code>$S$</code> eine <a href="http://de.wikipedia.org/wiki/Dreiecksmatrix#Unipotente_Dreiecksmatrizen">unipotente Dreiecksmatrix</a> ist und D eine positiv definite Diagonalmatrix.</p> <h2>Berechnung der Cholesky-Zerlegung</h2> <p>Hier ein paar Ausschnitte, aus der englischen Wikipedia:</p> <p>Einfach von links oben nach rechts unten die Werte nach folgender Formel berechnen: <code>$D_j = A_{jj} - \sum_{k=1}^{j-1} S_{jk}^2 D_k$</code> <code>$S_{ij} = \frac{1}{D_j} \left( A_{ij} - \sum_{k=1}^{j-1} S_{ik} S_{jk} D_k \right), \qquad\text{for } i&gt;j$</code></p> <h2>Programmierer-Hinweise</h2> <h3>Implementierung</h3> <p>Eine Python-Implementierung sieht so aus:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/env python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">getSD</span><span class="p">(</span><span class="n">A</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; @param A: eine quadratische, reele, positiv definite Matrix</span> <span class="sd"> @return: Die Matrizen S und D, f&amp;uuml;r die gilt:</span> <span class="sd"> A = S * D * S^T</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">S</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="n">D</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">S</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="mf">1.0</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">_summe</span> <span class="o">=</span> <span class="nb">sum</span><span class="p">(</span><span class="n">S</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">k</span><span class="p">]</span><span class="o">**</span><span class="mi">2</span> <span class="o">*</span> <span class="n">D</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">j</span><span class="p">))</span> <span class="n">D</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">A</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">_summe</span> <span class="n">_summe</span> <span class="o">=</span> <span class="nb">sum</span><span class="p">(</span><span class="n">S</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span><span class="o">*</span><span class="n">S</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">k</span><span class="p">]</span><span class="o">*</span><span class="n">D</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">j</span><span class="p">))</span> <span class="n">S</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="mf">1.0</span> <span class="o">/</span> <span class="n">D</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">*</span> <span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">-</span> <span class="n">_summe</span><span class="p">)</span> <span class="k">return</span> <span class="n">S</span><span class="p">,</span> <span class="n">D</span></code></pre></div> <h3>Bibliotheken</h3> <p>Ich habe mich mal nach Bibliotheken umgesehen, die die Cholesky-Zerlegung direkt beherrschen. NumPy kann es natürlich:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">linalg</span> <span class="k">print</span><span class="p">(</span><span class="n">linalg</span><span class="o">.</span><span class="n">cholesky</span><span class="p">([[</span><span class="mi">5</span><span class="p">,</span><span class="mi">1</span><span class="p">],[</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">]]))</span></code></pre></div> <p>Gibt aus:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">array<span class="o">([[</span> 2.23606798, 0. <span class="o">]</span>, <span class="o">[</span> 0.4472136 , 0.89442719<span class="o">]])</span></code></pre></div> <p>Das ist NICHT die Zerlegung <code>$A = S \cdot D \cdot S^T$</code>, sondern <code>$A = G \cdot G^T$</code>.</p> <p>Interessanterweise hat NumPy das nicht direkt selbst implementiert (<a href="https://github.com/numpy/numpy/blob/master/numpy/linalg/linalg.py#L448">NumPy-Quelle</a>). Man greift auf <a href="http://de.wikipedia.org/wiki/LAPACK">LAPACK</a> zurück, was in FORTRAN 90 programmiert wurde (<a href="http://www.netlib.org/lapack/double/dpotrf.f">LAPACK-Quelle</a>)!</p> <h3>Wolfram|Alpha</h3> <p>Auch Wolfram|Alpha kennt “cholesky decomposition”: <a href="http://www.wolframalpha.com/input/?i=cholesky+decomposition+%7B%7B5%2C2%7D%2C%7B2%2C1%7D%7D">Beispiel</a>. Allerdings sieht es schon bei <code>$3 \times 3$</code>-Matrizen schlecht aus.</p> <h2>Numerik</h2> <p>In Numerik haben wir bei Herrn Dr. Weiß folgendes als Cholesky-Zerlegung kennen gelernt:</p> <p>Sei <code>$A \in \mathbb{R}^{n \times n}$</code> eine symmetrische, positiv definite Matrix. Dann existiert eine Zerlegung <code>$A = \bar L \cdot \bar{L}^T$</code>, wobei <code>$\bar L$</code> eine untere Dreiecksmatrix ist.</p> <p>Wenn man wie gewohnt eine LR-Zerlegung der Matrix <code>$A$</code> durchführt, erhält man zwei Matrizen <code>$L, R \in \mathbb{R}^{n \times n}$</code>, wobei gilt: <code>$R = D \cdot L^T$</code>, wobei <code>$D$</code> eine positiv definite Diagonalmatrix ist.</p> <p>Offensichtlich gilt: <code>$\bar L = L \cdot D^{\frac{1}{2}}$</code>.</p> <p>Die Cholesky-Zerlegung kann man folgendermaßen berechnen:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/07/cholesky-zerlegung-numerik.png"><img src="../images/2012/07/cholesky-zerlegung-numerik.png" alt="Berechnung der Cholesky-Zerlegung in Pseudocode" width="" height="" class="size-full wp-image-67881" /></a><p class="wp-caption-text">Berechnung der Cholesky-Zerlegung in Pseudocode</p></div> <p>In Python sieht das dann so aus:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">getL</span><span class="p">(</span><span class="n">A</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">L</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">print</span><span class="p">(</span><span class="n">L</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;&quot;</span><span class="p">)</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">L</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">-</span> <span class="nb">sum</span><span class="p">([</span><span class="n">L</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">i</span><span class="p">]</span><span class="o">**</span><span class="mi">2</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">k</span><span class="p">)]))</span><span class="o">**</span><span class="mf">0.5</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">k</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="n">L</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">-</span> <span class="nb">sum</span><span class="p">([</span><span class="n">L</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span><span class="o">*</span><span class="n">L</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">k</span><span class="p">)]))</span> \ <span class="o">/</span> <span class="n">L</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="k">return</span> <span class="n">L</span></code></pre></div> <h2>Siehe auch</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Cholesky_decomposition">Cholesky decomposition</a> (Englisch)</li> <li><a href="http://de.wikipedia.org/wiki/Cholesky-Zerlegung">Cholesky-Zerlegung</a></li> </ul> George Carlin //martin-thoma.com/george-carlin/ Sun, 01 Jul 2012 19:49:23 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/george-carlin <p><a href="http://en.wikipedia.org/wiki/George_Carlin">George Carlin</a> is a great American stand-up comedian. Here are some of his clips:</p> <h2>Airplane Announcements</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/h7uMom9N5-I" frameborder="0" allowfullscreen=""></iframe> <iframe width="512" height="384" src="http://www.youtube.com/embed/feylIp-psJ0" frameborder="0" allowfullscreen=""></iframe> <h2>War</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/gnK8_KJcmWg" frameborder="0" allowfullscreen=""></iframe> <h2>Our Similarities</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/cgps85scy1g" frameborder="0" allowfullscreen=""></iframe> LaTeX + Versioning = A great Experience //martin-thoma.com/latex-versioning-a-great-experience/ Fri, 29 Jun 2012 22:52:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/latex-versioning-a-great-experience <p>Some people keep asking me questions like “Why do you use LaTeX?” - “Wouldn’t it be faster to do it with Word?”</p> <p>Here is the answer:</p> <ul> <li><strong>Versioning</strong>: I do quite often create repositories for documentation (e.g. on GITHub). Versioning LaTeX-files is much better than versioning Word-files, as LaTeX is line-based. Versioning is my way to solve the following problems: <ul> <li><strong>Dead end</strong>: Once in a while I stuck while writing. I tried to improve some part of the documentation, but it didn't work. So I want to jump back. It is much more convenient to jump back in a versioning system than to press <kbd>CTRL</kbd> + <kbd>Z</kbd> often or to create copies of the old version.</li> <li><strong>Versioning</strong>: This might sound strange, but versioning was a problem for me as I wrote my "Facharbeit" (a thesis you have to write in Germany at the end of secondary school). I had so many backups that I didn't know what was the original. If you use a versioning system, you can have everything in one place.</li> <li><strong>Simpler collaboration</strong>: Some weeks ago I had to prepare a <a href="http://cloud.github.com/downloads/MartinThoma/ICPC-Referat/Graphentheorie-2.pdf">presentation about graph algorithms</a> with three fellow students. We just met once to decide how to split the project. After that, everybody could work on his part while everybody could see the progress. We had no need of merging the documents. (See <a href="https://github.com/MartinThoma/ICPC-Referat">GITHub-Repository</a>)</li> <li><strong>Simpler proofreading</strong>: The proofreader can make a fork of the repository with the documentation and make changes on his copy. After that, the writer can make a diff and see if he wants to take those changes. You can't forget small changes of the proofreader (like a "," you forgot / you made too much) with diffs.</li> <li><strong>Backups</strong>: I've been ultra-paranoid as I wrote my thesis for secondary school. I regularly sent a copy to my father per Email and I had at least two copies on different data storage mediums. I wouldn't have needed this if I used versioning with GITHub. (I trust in the reliability of the service GITHub offers)</li> </ul> </li> <li><strong>Accessibility</strong>: To open LaTeX, you only need a text editor. If you want to complie it, you have to get one of many free LaTeX distributions like TeX-Live. After compiling it you get a PDF. PDFs look always the same, so you don't have the problem of shifted margins.</li> <li><strong>Speed</strong>: I can write mathematical formulae much faster with LaTeX than with Word.</li> <li><strong>Professional look</strong>: You can quite often see if a presentation / documentation was written with LaTeX or with Word. I think the LaTeX-Documentations do look much more professional.</li> <li><strong>Source Code Inclusion</strong>: You can include and highlight source code directly within LaTeX. No need for copy and paste (see <a href="../how-to-print-source-code-with-latex/" title="How to print Source Code with LaTeX">How to print Source Code with LaTeX</a>, <a href="../how-print-mips-assembly-code-latex/" title="How to print MIPS assembly code in LaTeX">How to print MIPS assembly code in LaTeX</a>)</li> <li><strong>Great Visualizations</strong>: You can create great visualizations directly within LaTeX (see , <a href="../how-to-draw-a-finite-state-machine/" title="How to draw a finite-state machine">How to draw a finite-state machine</a>, <a href="../plotting-function-graphs-with-latex/" title="Plotting function graphs with LaTeX">Plotting function graphs with LaTeX</a> and <a href="../complex-latex-visualizations-tikz/" title="Complex LaTeX visualizations (Tikz)">Complex LaTeX visualizations (Tikz)</a>)</li> </ul> <p>I guess some might not know what a diff is or how it can look like. diff is a program that compares text files. This is an example with two text files. Each of them has 100 paragraphs:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~/Desktop<span class="sb">`</span><span class="nv">$ </span>diff file1.txt file2.txt 127,128d126 &lt; And here is another one. &lt; 189c187 &lt; Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue dui s dolore te feugait nulla facilisi. --- &gt; Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue duis dolore te feugait nulla facilisi. 191c189 &lt; Nam liber tempor cum soluta nobis eleifend option congue nihil imperdiet doming id quod mazim placerat facer possim assum. Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nosnummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat. Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat. --- &gt; Nam liber tempor cum soluta nobis eleifend option congue nihil imperdiet doming id quod mazim placerat facer possim assum. Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat. Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat.</code></pre></div> <p>If you use meld it looks like this: <a href="../images/2012/06/meld-diff.png"><img src="../images/2012/06/meld-diff-300x156.png" alt="" title="meld-diff" width="300" height="156" class="aligncenter size-medium wp-image-29051" /></a></p> <h2>My LaTeX configuration</h2> <p>First, you have to install the latest LaTeX-Version: <a href="../how-to-install-the-latest-latex-version/" title="How to install the latest LaTeX Version">How to install the latest LaTeX Version</a>.</p> <p>I like editing the source code directly very much. To do so, I use gEdit. When I press <kbd>Ctrl</kbd>+<kbd>M</kbd>, my LaTeX document gets saved, compiled and the temporary files are thrown away. If you want this, you should follow these instructions.</p> <ul> <li>Create a "Makefile" (a file called this way) with this content in the folder where your LaTeX file is:</li> </ul> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>make: pdflatex matrix.tex -output-format=pdf make clean clean: rm -rf $(TARGET) *.class *.html *.log *.aux </pre></div> </div> </div> <ul> <li>Enable the Plugin "External Tools"</li> <li>Go to Preferences &rarr; Plugins &rarr; External Tools &rarr; Configure Plugin</li> <li>Click on the New Page icon</li> <li>Insert "make" into the Edit-Window</li> <li>Create the Shortcut Key. I've added <kbd>Ctrl</kbd>+<kbd>M</kbd>.</li> </ul> <h2>See also</h2> <ul> <li><a href="http://academia.stackexchange.com/a/5281/4092">Why use version control systems for writing a paper</a> instead of Dropbox</li> </ul> Complex LaTeX visualizations (Tikz) //martin-thoma.com/complex-latex-visualizations-tikz/ Fri, 29 Jun 2012 18:38:27 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/complex-latex-visualizations-tikz <p>You can create some very complex visualizations with LaTeX. Take a look at these:</p> <div style="width: 332px" class="wp-caption aligncenter"><a href="../images/2012/06/circumscribed-polygons-and-circles.png"><img src="../images/2012/06/circumscribed-polygons-and-circles.png" alt="Circumscribed polygons and circles" width="" height="" class="size-full wp-image-28871" /></a><p class="wp-caption-text">Circumscribed polygons and circles</p></div> <p>Used matlab Source: <a href="http://www.texample.net/tikz/examples/circumscribed-polygons-and-circles/">texample.net</a></p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2012/06/mosaik-from-pompeii.png"><img src="../images/2012/06/mosaik-from-pompeii.png" alt="Mosaic from Pompeii" width="" height="" class="size-full wp-image-28881" /></a><p class="wp-caption-text">Mosaic from Pompeii</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/mosaic-from-pompeii/">texample.net</a></p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2012/06/dandelin-spheres.png"><img src="../images/2012/06/dandelin-spheres.png" alt="Plane Sections of the Cylinder - Dandelin Spheres" width="" height="" class="size-full wp-image-28891" /></a><p class="wp-caption-text">Plane Sections of the Cylinder - Dandelin Spheres</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/dandelin-spheres/">texample.net</a></p> <div style="width: 482px" class="wp-caption aligncenter"><a href="../images/2012/06/dipolar-magnetic-field.png"><img src="../images/2012/06/dipolar-magnetic-field.png" alt="Example: Dipolar magnetic field" width="" height="" class="size-full wp-image-28901" /></a><p class="wp-caption-text">Example: Dipolar magnetic field</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/dipolar-magnetic-field/">texample.net</a></p> <div style="width: 418px" class="wp-caption aligncenter"><a href="../images/2012/06/gamma-interaction.png"><img src="../images/2012/06/gamma-interaction.png" alt="Gamma interaction" width="" height="" class="size-full wp-image-28921" /></a><p class="wp-caption-text">Gamma interaction</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/gamma-interaction/">texample.net</a></p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2012/06/complete-graph.png"><img src="../images/2012/06/complete-graph.png" alt="A complete graph" width="" height="" class="size-full wp-image-28931" /></a><p class="wp-caption-text">A complete graph</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/complete-graph/">texample.net</a></p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2012/06/mandala.png"><img src="../images/2012/06/mandala.png" alt="Mandala" width="" height="" class="size-full wp-image-28951" /></a><p class="wp-caption-text">Mandala</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/mandala/">texample.net</a></p> <div style="width: 507px" class="wp-caption aligncenter"><a href="../images/2012/06/pascals-triangle.png"><img src="../images/2012/06/pascals-triangle.png" alt="Pascal&rsquo;s triangle and Sierpinski triangle" width="" height="" class="size-full wp-image-28961" /></a><p class="wp-caption-text">Pascal&rsquo;s triangle and Sierpinski triangle</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/pascals-triangle-and-sierpinski-triangle/">texample.net</a></p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/06/seismic-focal-mechanism.png"><img src="../images/2012/06/seismic-focal-mechanism.png" alt="Seismic focal mechanism in 3D view" width="" height="" class="size-full wp-image-28971" /></a><p class="wp-caption-text">Seismic focal mechanism in 3D view</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/seismic-focal-mechanism-in-3d-view/">texample.net</a></p> <div style="width: 502px" class="wp-caption aligncenter"><a href="../images/2012/06/membrane-surface.png"><img src="../images/2012/06/membrane-surface.png" alt="Membrane-like surface" width="" height="" class="size-full wp-image-28981" /></a><p class="wp-caption-text">Membrane-like surface</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/membrane-surface/">texample.net</a></p> <div style="width: 504px" class="wp-caption aligncenter"><a href="../images/2012/06/mindmap.png"><img src="../images/2012/06/mindmap.png" alt="Computer science mindmap" width="" height="" class="size-full wp-image-28991" /></a><p class="wp-caption-text">Computer science mindmap</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/computer-science-mindmap/">texample.net</a></p> <div style="width: 487px" class="wp-caption aligncenter"><a href="../images/2012/06/spherical-and-cartesian-grids.png"><img src="../images/2012/06/spherical-and-cartesian-grids.png" alt="Spherical and cartesian grids" width="" height="" class="size-full wp-image-29001" /></a><p class="wp-caption-text">Spherical and cartesian grids</p></div> <p>Source: <a href="http://www.texample.net/tikz/examples/spherical-and-cartesian-grids/">texample.net</a></p> <p>Do you know more? Please leave a comment!</p> <h2>See also</h2> <ul> <li><a href="http://tex.stackexchange.com/q/61437/5645">Penrose tiling in TikZ</a></li> <li><a href="http://www.texample.net/tikz/examples/lindenmayer-systems/">Lindenmayer systems</a></li> <li><a href="http://tex.stackexchange.com/q/54341/5645">How to draw nanotubes with TeX</a></li> </ul> Perfect number check and ROT-13 encryption in MIPS-assembly code //martin-thoma.com/perfect-number-check-rot-13-encryption-mips-assembly-code/ Fri, 22 Jun 2012 10:43:49 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/perfect-number-check-rot-13-encryption-mips-assembly-code <h2>Perfect number check</h2> <p>The perfect number check in MIPS is quite easy to realize. Here is some pythonic Pseudocode</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">n</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="c"># read a positive integer n from the user</span> <span class="n">sumOfDivisors</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">n</span><span class="p">):</span> <span class="c"># go from 1 to n-1</span> <span class="k">if</span> <span class="n">n</span> <span class="o">%</span> <span class="n">i</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="c"># if i is a divisor</span> <span class="n">sumOfDivisors</span> <span class="o">+=</span> <span class="n">i</span> <span class="k">if</span> <span class="n">sumOfDivisors</span> <span class="o">==</span> <span class="n">n</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;1&quot;</span> <span class="k">else</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;0&quot;</span></code></pre></div> <p>And here is the MIPS-Code:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">##################################################################### # Perfect number check # # @param int the number you would like to check # # @result int 0 if the number is not perfect, otherwise 1 # ##################################################################### .data prompt: .asciiz &quot;Positive integer you would like to check : &quot; output: .asciiz &quot;Is a perfect number (1: Yes, 0: No): &quot; .text .globl main main: li `$v0 , 4 # | la $`a0 , prompt # | syscall # |=&gt; Print string &quot;prompt&quot; li `$v0 , 5 # | syscall # |=&gt; Ask for integer A # Initialise variables move $`s0 , `$v0 # =&gt; Store A in $`s0 li `$s1 , 0 # =&gt; The sum of all proper divisors of A li $`s2 , 1 # =&gt; start here with checks for devisors s: bgeu `$s2, $`s0, eval # while `$s2 &lt; $`s0 rem `$t0, $`s0, `$s2 # $`t0 = `$s0 % $`s2 bne `$t0, $`0, w addu `$s1, $`s1, `$s2 # $`s1 += `$s2 w: addi $`s2, `$s2, 1 # $`s2++ j s; # /endwhile eval: seq `$s0, $`s0, `$s1 # Compare the sum of divisors with A li $`v0 , 4 # | la `$a0 , output # | syscall # |=&gt; Print string &quot;output&quot; la $`v0 , 1 # | move `$a0 , $`s0 # | syscall # |=&gt; Print `$s0 jr $`ra</code></pre></div> <h2>ROT-13 encryption</h2> <p>The basic idea for encrypting a string with ROT-13 is to loop over all characters and use the ASCII-Table to shift them. Here is the ROT-13 MIPS-Code:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">##################################################################### # @param string a &amp;#92;&amp;#48; terminated string # # @return string the ROT-13 encrypted string # ##################################################################### .data prompt: .asciiz &quot;Please enter string: &quot; output: .asciiz &quot;ROT-13: &quot; plain: .space 64 .text .globl main main: li `$v0, 4 # | la $`a0, prompt # | syscall # |=&gt; Print string &quot;prompt&quot; li `$v0, 8 # | la $`a0, plain # | =&gt; Ask for string plain li `$a1, 64 # | syscall # | =&gt; read a string with max. 64 chars li $`t2, 10 # Stop by \n # Loop over all characters la `$t1, ($`a0) #=&gt;`$t1:the current adress that gets modified s: lb $`t0, (`$t1) # =&gt; $`t0: the current value (char) beq `$t0, $`t2, out # while `$t1 != &#39;\n&#39; li $`t3, 64 bge `$t3, $`t0, w # if `$t0 &lt;= 64: jump to w li $`t3, 123 bge `$t0, $`t3, w # if `$t0 &gt;= 123: jump to w li $`t3, 90 bge `$t3, $`t0, big # if `$t0 &lt;= 90: jump to big li $`t3, 96 bge `$t3, $`t0, w # if `$t0 &lt;= 96: jump to w j small w: addi $`t1, `$t1, 1 # $`t1++ j s; # /endwhile small: addi `$t0, -84 # -97 + 13 rem $`t0, `$t0, 26 # $`t0 %= 26 addi `$t0, 97 sb $`t0, (`$t1) j w big: addi $`t0, -52 # -65 + 13 rem `$t0, $`t0, 26 # `$t0 %= 26 addi $`t0, 65 sb `$t0, ($`t1) j w out: li `$v0, 4 # | la $`a0, output # | syscall # |=&gt; Print string &quot;output&quot; la `$v0, 4 # | la $`a0, plain # | syscall # |=&gt; Print plain jr $ra</code></pre></div> <p>A syntax-highlighted version of both code pieces is here: <a href="../images/2012/06/mips-rot-13-perfect-number.pdf">MIPS Assembly Code for a perfect number check and ROT-13 encryption</a>.</p> <h2>See also</h2> <ul> <li><a href="https://sourceforge.net/projects/spimsimulator/files/">SPIM MIPS Simulator</a></li> <li><a href="../how-print-mips-assembly-code-latex/" title="How to print MIPS assembly code in LaTeX">How to print MIPS assembly code in LaTeX</a></li> <li><a href="../add-mips-syntax-highlighting-gedit/" title="Add MIPS syntax highlighting to gEdit">Add MIPS syntax highlighting to gEdit</a></li> <li><a href="../images/2012/06/mips-archive.zip">Archive with MIPS assembly Code and LaTeX file</a></li> </ul> Part I: Performance of Matrix multiplication in Python, Java and C++ //martin-thoma.com/matrix-multiplication-python-java-cpp/ Mon, 18 Jun 2012 21:37:46 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/matrix-multiplication-python-java-cpp <div class="info">This is Part I of my matrix multiplication series. <a href="../matrix-multiplication-python-java-cpp/">Part I</a> was about simple matrix multiplication algorithms and <a href="../strassen-algorithm-in-python-java-cpp/">Part II</a> was about the Strassen algorithm. <a href="../part-iii-matrix-multiplication-on-multiple-cores-in-python-java-and-c/">Part III</a> is about parallel matrix multiplication.</div> <p>This post is about simple implementations of matrix multiplications. The goal of this post is to find out how easy it is to implement a matrix multiplication in Python, Java and C++. Additionally, I want to get to know how good these solutions are.</p> <p>The second post will be an implementation of the Strassen algorithm for matrix multiplication. <a href="http://en.wikipedia.org/wiki/Strassen_algorithm">Strassen algorithm</a> does matrix multiplication in <code>$\cal O(n^{log_2(7)+o(1)}) \approx \cal O(n^{2.807})$</code> instead of <code>$\cal O(n^3)$</code>. I am quite sure this will outperform almost every other change. See Part II: <a href="../strassen-algorithm-in-python-java-cpp/">The Strassen algorithm in Python, Java and C++</a>.</p> <p>The third post will be about parallel programming. I have two cores and I want to see if it will be significantly faster if I use both of them.</p> <h2>The implementations</h2> <p>I will post all scripts for this test and I’ve added a <a href="https://github.com/MartinThoma/matrix-multiplication">GIT repository</a>, so feel free to test it on your machine. I am also happy if you post some of your solutions with running times ☺ I am quite sure that my Java and C++ code can be written much better. If you know how, please leave a comment. If you know other languages, you could create a script for these. I focus on Python, Java and C++ as they are very often used.</p> <p>I have implemented these three types of algorithms for this post:</p> <ul> <li><strong>ijk-algorithm</strong>: This is a simple, straight forward implementation of a matrix multiplication. I've used the definition of matrix multiplication. I didn't use multiple threads.</li> <li><strong>ikj-algorithm</strong>: just like the ijk-algorithm, but I've switched two of the three the for-loops.</li> <li><strong>Library-functions</strong>: I always prefer libraries over self-implemented solutions. I think they are faster than anything I could come up with in a reasonable amount of time.</li> </ul> <p>If you post a solution, please consider these restrictions:</p> <ul> <li><strong>Input</strong>: The input file should get passed with the parameter <code>-i</code>, e.g.: <code>python -i 2000.in</code> or <code>java Shell -i 2000.in</code></li> <li>The standard value for the command line parameter -i should be "2000.in" (a `$2000 \times 2000$` matrix)</li> <li>The user should <em>not</em> have to give the size of the matrix!</li> <li>The two square-matrices that should get multiplied are ... <ul> <li>... read from a text-file.</li> <li>... represented like this: <ul> <li>Every line of one matrix is one line in the text-file.</li> <li>Newlines are only "\n".</li> <li>Every number is separated by "\t".</li> <li>The both matrices are separated by one newline.</li> </ul> </li> </ul> </li> <li><strong>Output</strong>: The result has to get printed to standard output.</li> <li>The result has to be formatted like the input (tabs for separation of number, \n for marks a new line)</li> </ul> <h2>The Tests</h2> <p>I will check the speed of a multiplication of two big matrices following for Python, Java and C++ for all algorithms like this:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>python scriptABC.py -i ../2000.in &gt; result.txt diff result.txt bigMatrix.out</code></pre></div> <p>The <code>bigMatrix.out</code> was produced by the Python ijk-implementation. I make the diff to test if the result is correct.</p> <h2>The Setting</h2> <p>I created two “random” matrices <code>$A, B \in \mathbb{N}^{2000 \times 2000}$</code> with this script. The file that was created needs about 29.7 MB and is also in the GIT-Hub repository. But you can also create the matrices with this script:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">random</span> <span class="n">random</span><span class="o">.</span><span class="n">seed</span><span class="p">(</span><span class="mi">1234</span><span class="p">)</span> <span class="k">def</span> <span class="nf">createRandomMatrix</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">maxVal</span> <span class="o">=</span> <span class="mi">1000</span> <span class="c"># I don&#39;t want to get Java / C++ into trouble</span> <span class="n">matrix</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">([</span><span class="n">random</span><span class="o">.</span><span class="n">randint</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="n">maxVal</span><span class="p">)</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)])</span> <span class="k">return</span> <span class="n">matrix</span> <span class="k">def</span> <span class="nf">saveMatrix</span><span class="p">(</span><span class="n">matrixA</span><span class="p">,</span> <span class="n">matrixB</span><span class="p">,</span> <span class="n">filename</span><span class="p">):</span> <span class="n">f</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;w&#39;</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span><span class="p">,</span> <span class="n">matrix</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">([</span><span class="n">matrixA</span><span class="p">,</span> <span class="n">matrixB</span><span class="p">]):</span> <span class="k">if</span> <span class="n">i</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">)</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span> <span class="n">line</span><span class="p">))</span> <span class="o">+</span> <span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">)</span> <span class="n">n</span> <span class="o">=</span> <span class="mi">3</span> <span class="n">matrixA</span> <span class="o">=</span> <span class="n">createRandomMatrix</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="n">matrixB</span> <span class="o">=</span> <span class="n">createRandomMatrix</span><span class="p">(</span><span class="n">n</span><span class="p">)</span> <span class="n">saveMatrix</span><span class="p">(</span><span class="n">matrixA</span><span class="p">,</span> <span class="n">matrixB</span><span class="p">,</span> <span class="s">&quot;2000.in&quot;</span><span class="p">)</span></code></pre></div> <p>All scripts are tested on my computer:</p> <table> <tr> <td colspan="2" style="background-color:#cdcdcd">Acer TravelMate 5735Z</td> </tr> <tr> <td style="background-color:#efefef">CPU</td> <td>2x Pentium(R) Dual-Core CPU T4500 @2.30GHz</td> </tr> <tr> <td style="background-color:#efefef">RAM</td> <td>4 GB</td> </tr> <tr> <td style="background-color:#efefef">Video Card</td> <td>Intel GMA 4500MHD</td> </tr> <tr> <td style="background-color:#efefef">System</td> <td>Ubuntu 10.10.04 LTS</td> </tr> </table> <h2>Python</h2> <p>I’ve used Python 2.6.5.</p> <h3>ijk-algorithm</h3> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">optparse</span> <span class="kn">import</span> <span class="n">OptionParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">OptionParser</span><span class="p">()</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_option</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;2000.in&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="p">(</span><span class="n">options</span><span class="p">,</span> <span class="n">args</span><span class="p">)</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">A</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="k">if</span> <span class="n">line</span> <span class="o">!=</span> <span class="s">&quot;&quot;</span><span class="p">:</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">else</span><span class="p">:</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">):</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="k">def</span> <span class="nf">standardMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">options</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">standardMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">)</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">)</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 56m49.266s user 56m30.524s sys 0m2.980s</code></pre></div> <h3>ikj-algorithm</h3> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">ikjMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 44m36.507s user 44m13.458s sys 0m2.000s</code></pre></div> <h3>Psyco ikj-algorithm</h3> <p><a href="http://en.wikipedia.org/wiki/Psyco">Psyco</a> is a just in time compiler, which makes my scripts MUCH faster. It is very simple to use. Add these two lines at the top of the ikj-script:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">import</span> <span class="nn">psyco</span> <span class="n">psyco</span><span class="o">.</span><span class="n">full</span><span class="p">()</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 6m14.820s user 6m12.959s sys 0m0.620s</code></pre></div> <p>Amazing, isn’t it?</p> <h3>Libraries</h3> <h4>NumPy</h4> <p>NumPy-Version: 1.3.0 (Current version is 1.6.2, see <a href="http://en.wikipedia.org/wiki/NumPy">Wiki</a>)</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">from</span> <span class="nn">optparse</span> <span class="kn">import</span> <span class="n">OptionParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">OptionParser</span><span class="p">()</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_option</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;2000.in&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="p">(</span><span class="n">options</span><span class="p">,</span> <span class="n">args</span><span class="p">)</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">A</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="k">if</span> <span class="n">line</span> <span class="o">!=</span> <span class="s">&quot;&quot;</span><span class="p">:</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">else</span><span class="p">:</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">):</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">array</span><span class="p">(</span><span class="n">matrix</span><span class="p">)</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">options</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">A</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">B</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">A</span> <span class="o">*</span> <span class="n">B</span> <span class="c"># easy and intuitive, isn&#39;t it?</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">)</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 1m38.425s user 1m36.066s sys 0m0.520s</code></pre></div> <h4>SciPy</h4> <p>You might need to install <code>python-scitools</code>.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="nn">scipy</span> <span class="kn">from</span> <span class="nn">optparse</span> <span class="kn">import</span> <span class="n">OptionParser</span> <span class="n">parser</span> <span class="o">=</span> <span class="n">OptionParser</span><span class="p">()</span> <span class="n">parser</span><span class="o">.</span><span class="n">add_option</span><span class="p">(</span><span class="s">&quot;-i&quot;</span><span class="p">,</span> <span class="n">dest</span><span class="o">=</span><span class="s">&quot;filename&quot;</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&quot;2000.in&quot;</span><span class="p">,</span> <span class="n">help</span><span class="o">=</span><span class="s">&quot;input file with two matrices&quot;</span><span class="p">,</span> <span class="n">metavar</span><span class="o">=</span><span class="s">&quot;FILE&quot;</span><span class="p">)</span> <span class="p">(</span><span class="n">options</span><span class="p">,</span> <span class="n">args</span><span class="p">)</span> <span class="o">=</span> <span class="n">parser</span><span class="o">.</span><span class="n">parse_args</span><span class="p">()</span> <span class="k">def</span> <span class="nf">read</span><span class="p">(</span><span class="n">filename</span><span class="p">):</span> <span class="n">lines</span> <span class="o">=</span> <span class="nb">open</span><span class="p">(</span><span class="n">filename</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span><span class="o">.</span><span class="n">read</span><span class="p">()</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">A</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">lines</span><span class="p">:</span> <span class="k">if</span> <span class="n">line</span> <span class="o">!=</span> <span class="s">&quot;&quot;</span><span class="p">:</span> <span class="n">matrix</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">)))</span> <span class="k">else</span><span class="p">:</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">B</span> <span class="k">return</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="k">def</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">matrix</span><span class="p">):</span> <span class="n">matrix</span> <span class="o">=</span> <span class="n">numpy</span><span class="o">.</span><span class="n">array</span><span class="p">(</span><span class="n">matrix</span><span class="p">)</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">matrix</span><span class="p">:</span> <span class="k">print</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="n">line</span><span class="p">))</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">read</span><span class="p">(</span><span class="n">options</span><span class="o">.</span><span class="n">filename</span><span class="p">)</span> <span class="n">A</span> <span class="o">=</span> <span class="n">scipy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">B</span> <span class="o">=</span> <span class="n">scipy</span><span class="o">.</span><span class="n">matrix</span><span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="n">A</span> <span class="o">*</span> <span class="n">B</span> <span class="c"># easy and intuitive, isn&#39;t it?</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">)</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 1m35.795s user 1m33.438s sys 0m0.488s</code></pre></div> <h3>Conclusion for Python</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/06/python-execution-times.png"><img src="../images/2012/06/python-execution-times.png" alt="Python execution times for matrix multiplication" width="" height="" class="size-full wp-image-28301" /></a><p class="wp-caption-text">Python execution times for matrix multiplication</p></div> <p>Using NumPy is by far the easiest and fastest option. I’ve needed about five minutes for each of the non-library scripts and about 10 minutes for the NumPy/SciPy scripts.</p> <p>By the way, it is useless to combine Psyco and NumPy. It gets a little bit faster (1 minute and 28 seconds), but this could also be a random effect. If you execute it many times, you will see that the execution time is never the same.</p> <h2>Java</h2> <p>I am using this Java version:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="sb">`</span><span class="nv">$ </span>java -version java version <span class="s2">&quot;1.6.0_20&quot;</span> OpenJDK Runtime Environment <span class="o">(</span>IcedTea6 1.9.13<span class="o">)</span> <span class="o">(</span>6b20-1.9.13-0ubuntu1~10.04.1<span class="o">)</span> OpenJDK Server VM <span class="o">(</span>build 19.0-b09, mixed mode<span class="o">)</span></code></pre></div> <h3>ijk-algorithm</h3> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.io.BufferedReader</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.FileReader</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.IOException</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.LinkedList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Shell</span> <span class="o">{</span> <span class="kd">static</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="nf">read</span><span class="o">(</span><span class="n">String</span> <span class="n">filename</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;();</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;();</span> <span class="n">String</span> <span class="n">thisLine</span><span class="o">;</span> <span class="k">try</span> <span class="o">{</span> <span class="n">BufferedReader</span> <span class="n">br</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">BufferedReader</span><span class="o">(</span> <span class="k">new</span> <span class="nf">FileReader</span><span class="o">(</span><span class="n">filename</span><span class="o">));</span> <span class="c1">// Begin reading A</span> <span class="k">while</span> <span class="o">((</span><span class="n">thisLine</span> <span class="o">=</span> <span class="n">br</span><span class="o">.</span><span class="na">readLine</span><span class="o">())</span> <span class="o">!=</span> <span class="kc">null</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">thisLine</span><span class="o">.</span><span class="na">trim</span><span class="o">().</span><span class="na">equals</span><span class="o">(</span><span class="s">&quot;&quot;</span><span class="o">))</span> <span class="o">{</span> <span class="k">break</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">line</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">String</span><span class="o">[]</span> <span class="n">lineArray</span> <span class="o">=</span> <span class="n">thisLine</span><span class="o">.</span><span class="na">split</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">String</span> <span class="n">number</span> <span class="o">:</span> <span class="n">lineArray</span><span class="o">)</span> <span class="o">{</span> <span class="n">line</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">number</span><span class="o">));</span> <span class="o">}</span> <span class="n">A</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">line</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="c1">// Begin reading B</span> <span class="k">while</span> <span class="o">((</span><span class="n">thisLine</span> <span class="o">=</span> <span class="n">br</span><span class="o">.</span><span class="na">readLine</span><span class="o">())</span> <span class="o">!=</span> <span class="kc">null</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">line</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">String</span><span class="o">[]</span> <span class="n">lineArray</span> <span class="o">=</span> <span class="n">thisLine</span><span class="o">.</span><span class="na">split</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">String</span> <span class="n">number</span> <span class="o">:</span> <span class="n">lineArray</span><span class="o">)</span> <span class="o">{</span> <span class="n">line</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">number</span><span class="o">));</span> <span class="o">}</span> <span class="n">B</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">line</span><span class="o">);</span> <span class="o">}</span> <span class="n">br</span><span class="o">.</span><span class="na">close</span><span class="o">();</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">IOException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Error: &quot;</span> <span class="o">+</span> <span class="n">e</span><span class="o">);</span> <span class="o">}</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="n">res</span> <span class="o">=</span> <span class="k">new</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;();</span> <span class="n">res</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">A</span><span class="o">);</span> <span class="n">res</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">B</span><span class="o">);</span> <span class="k">return</span> <span class="n">res</span><span class="o">;</span> <span class="o">}</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">ijkAlgorithm</span><span class="o">(</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span><span class="o">,</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">();</span> <span class="c1">// initialise C</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">k</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">+=</span> <span class="n">A</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">k</span><span class="o">)</span> <span class="o">*</span> <span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">k</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">printMatrix</span><span class="o">(</span><span class="kt">int</span><span class="o">[][]</span> <span class="n">matrix</span><span class="o">)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span><span class="o">[]</span> <span class="n">line</span> <span class="o">:</span> <span class="n">matrix</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">StringBuilder</span> <span class="n">sb</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">StringBuilder</span><span class="o">(</span><span class="n">matrix</span><span class="o">.</span><span class="na">length</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">number</span> <span class="o">:</span> <span class="n">line</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">i</span> <span class="o">!=</span> <span class="mi">0</span><span class="o">)</span> <span class="o">{</span> <span class="n">sb</span><span class="o">.</span><span class="na">append</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">i</span><span class="o">++;</span> <span class="o">}</span> <span class="n">sb</span><span class="o">.</span><span class="na">append</span><span class="o">(</span><span class="n">number</span><span class="o">);</span> <span class="o">}</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">sb</span><span class="o">.</span><span class="na">toString</span><span class="o">());</span> <span class="o">}</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">String</span> <span class="n">filename</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">args</span><span class="o">.</span><span class="na">length</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="o">)</span> <span class="o">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;2000.in&quot;</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">args</span><span class="o">[</span><span class="mi">1</span><span class="o">];</span> <span class="o">}</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;&gt;</span> <span class="n">matrices</span> <span class="o">=</span> <span class="n">read</span><span class="o">(</span><span class="n">filename</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="n">ijkAlgorithm</span><span class="o">(</span><span class="n">A</span><span class="o">,</span> <span class="n">B</span><span class="o">);</span> <span class="n">printMatrix</span><span class="o">(</span><span class="n">C</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 27m21.295s user 26m53.877s sys 0m4.368s</code></pre></div> <p>Note: Java is not C++! If you use <a href="http://docs.oracle.com/javase/6/docs/api/java/util/Vector.html">Vector</a> instead of <a href="http://docs.oracle.com/javase/6/docs/api/java/util/ArrayList.html">ArrayList</a>, you get these results:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 82m26.754s user 80m42.003s sys 0m24.598s</code></pre></div> <p>One reason might be that Vector is synchronized.</p> <h3>ikj-algoirthm</h3> <p>I’ve only switched line 60 and line 61.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 2m9.478s user 1m26.369s sys 0m39.162s</code></pre></div> <h3>Library: JAMA</h3> <p>I’ve searched in Google for “java matrix multiplication”. The first 10 results were only implementations of the ijk-algorithm. Although the ijk-algorithm is very easy, most of the results were only questions where people tried to implement it.</p> <p>After some search (20 minutes minimum) I’ve found <a href="http://math.nist.gov/javanumerics/jama/">JAMA</a>. They also have a <a href="http://math.nist.gov/javanumerics/jama/doc/">documentation</a>. You might need to install this for the following code:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install libjama-*</code></pre></div> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.io.BufferedReader</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.FileReader</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.io.IOException</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.ArrayList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.LinkedList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">Jama.Matrix</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">Shell</span> <span class="o">{</span> <span class="kd">static</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;&gt;</span> <span class="nf">read</span><span class="o">(</span><span class="n">String</span> <span class="n">filename</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;();</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;();</span> <span class="n">String</span> <span class="n">thisLine</span><span class="o">;</span> <span class="k">try</span> <span class="o">{</span> <span class="n">BufferedReader</span> <span class="n">br</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">BufferedReader</span><span class="o">(</span><span class="k">new</span> <span class="nf">FileReader</span><span class="o">(</span><span class="n">filename</span><span class="o">));</span> <span class="c1">// Begin reading A</span> <span class="k">while</span> <span class="o">((</span><span class="n">thisLine</span> <span class="o">=</span> <span class="n">br</span><span class="o">.</span><span class="na">readLine</span><span class="o">())</span> <span class="o">!=</span> <span class="kc">null</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">thisLine</span><span class="o">.</span><span class="na">trim</span><span class="o">().</span><span class="na">equals</span><span class="o">(</span><span class="s">&quot;&quot;</span><span class="o">))</span> <span class="o">{</span> <span class="k">break</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;</span> <span class="n">line</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;();</span> <span class="n">String</span><span class="o">[]</span> <span class="n">lineArray</span> <span class="o">=</span> <span class="n">thisLine</span><span class="o">.</span><span class="na">split</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">String</span> <span class="n">number</span> <span class="o">:</span> <span class="n">lineArray</span><span class="o">)</span> <span class="o">{</span> <span class="n">line</span><span class="o">.</span><span class="na">add</span><span class="o">((</span><span class="kt">double</span><span class="o">)</span> <span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">number</span><span class="o">));</span> <span class="o">}</span> <span class="n">A</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">line</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="c1">// Begin reading B</span> <span class="k">while</span> <span class="o">((</span><span class="n">thisLine</span> <span class="o">=</span> <span class="n">br</span><span class="o">.</span><span class="na">readLine</span><span class="o">())</span> <span class="o">!=</span> <span class="kc">null</span><span class="o">)</span> <span class="o">{</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;</span> <span class="n">line</span> <span class="o">=</span> <span class="k">new</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;();</span> <span class="n">String</span><span class="o">[]</span> <span class="n">lineArray</span> <span class="o">=</span> <span class="n">thisLine</span><span class="o">.</span><span class="na">split</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="k">for</span> <span class="o">(</span><span class="n">String</span> <span class="n">number</span> <span class="o">:</span> <span class="n">lineArray</span><span class="o">)</span> <span class="o">{</span> <span class="n">line</span><span class="o">.</span><span class="na">add</span><span class="o">((</span><span class="kt">double</span><span class="o">)</span> <span class="n">Integer</span><span class="o">.</span><span class="na">parseInt</span><span class="o">(</span><span class="n">number</span><span class="o">));</span> <span class="o">}</span> <span class="n">B</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">line</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="k">catch</span> <span class="o">(</span><span class="n">IOException</span> <span class="n">e</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">err</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Error: &quot;</span> <span class="o">+</span> <span class="n">e</span><span class="o">);</span> <span class="o">}</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;&gt;</span> <span class="n">res</span> <span class="o">=</span> <span class="k">new</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;&gt;();</span> <span class="n">res</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">A</span><span class="o">);</span> <span class="n">res</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="n">B</span><span class="o">);</span> <span class="k">return</span> <span class="n">res</span><span class="o">;</span> <span class="o">}</span> <span class="kd">static</span> <span class="kt">int</span><span class="o">[][]</span> <span class="nf">ijkAlgorithm</span><span class="o">(</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">A</span><span class="o">,</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;&gt;</span> <span class="n">B</span><span class="o">)</span> <span class="o">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">();</span> <span class="c1">// initialise C</span> <span class="kt">int</span><span class="o">[][]</span> <span class="n">C</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">k</span><span class="o">++)</span> <span class="o">{</span> <span class="n">C</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">+=</span> <span class="n">A</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">k</span><span class="o">)</span> <span class="o">*</span> <span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">k</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="o">}</span> <span class="k">return</span> <span class="n">C</span><span class="o">;</span> <span class="o">}</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">printMatrix</span><span class="o">(</span><span class="n">Matrix</span> <span class="n">matrix</span><span class="o">,</span> <span class="kt">int</span> <span class="n">n</span><span class="o">)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">j</span> <span class="o">!=</span> <span class="mi">0</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">print</span><span class="o">(</span><span class="s">&quot;\t&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">printf</span><span class="o">(</span><span class="s">&quot;%.0f&quot;</span><span class="o">,</span> <span class="n">matrix</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">,</span> <span class="n">j</span><span class="o">));</span> <span class="o">}</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;&quot;</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">String</span> <span class="n">filename</span><span class="o">;</span> <span class="k">if</span> <span class="o">(</span><span class="n">args</span><span class="o">.</span><span class="na">length</span> <span class="o">&lt;</span> <span class="mi">2</span><span class="o">)</span> <span class="o">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;2000.in&quot;</span><span class="o">;</span> <span class="o">}</span> <span class="k">else</span> <span class="o">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">args</span><span class="o">[</span><span class="mi">1</span><span class="o">];</span> <span class="o">}</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;&gt;</span> <span class="n">matrices</span> <span class="o">=</span> <span class="n">read</span><span class="o">(</span><span class="n">filename</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;</span> <span class="n">A</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">0</span><span class="o">);</span> <span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">ArrayList</span><span class="o">&lt;</span><span class="n">Double</span><span class="o">&gt;&gt;</span> <span class="n">B</span> <span class="o">=</span> <span class="n">matrices</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">size</span><span class="o">();</span> <span class="kt">double</span><span class="o">[][]</span> <span class="n">Aarray</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">double</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="kt">double</span><span class="o">[][]</span> <span class="n">Barray</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">double</span><span class="o">[</span><span class="n">n</span><span class="o">][</span><span class="n">n</span><span class="o">];</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="o">;</span> <span class="n">j</span><span class="o">++)</span> <span class="o">{</span> <span class="n">Aarray</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">A</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="n">Barray</span><span class="o">[</span><span class="n">i</span><span class="o">][</span><span class="n">j</span><span class="o">]</span> <span class="o">=</span> <span class="n">B</span><span class="o">.</span><span class="na">get</span><span class="o">(</span><span class="n">i</span><span class="o">).</span><span class="na">get</span><span class="o">(</span><span class="n">j</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span> <span class="n">Matrix</span> <span class="n">AM</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Matrix</span><span class="o">(</span><span class="n">Aarray</span><span class="o">);</span> <span class="n">Matrix</span> <span class="n">BM</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">Matrix</span><span class="o">(</span><span class="n">Aarray</span><span class="o">);</span> <span class="n">Matrix</span> <span class="n">CM</span> <span class="o">=</span> <span class="n">AM</span><span class="o">.</span><span class="na">times</span><span class="o">(</span><span class="n">BM</span><span class="o">);</span> <span class="n">printMatrix</span><span class="o">(</span><span class="n">CM</span><span class="o">,</span> <span class="n">n</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 1m36.506s user 0m51.367s sys 0m45.043s</code></pre></div> <p>It took me about two hours to get it work. I had to add the JAMA-JAR to eclipse, export my project as a JAR and run it with</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">time </span>java -jar jama-shell.jar -i ../2000.in &gt; jama-result.out</code></pre></div> <p>I still have no idea how to compile it with bash only.</p> <h3>Conclusion for Java</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/06/java-execution-time.png"><img src="../images/2012/06/java-execution-time.png" alt="Java execution times for matrix multiplication" width="" height="" class="size-full wp-image-28331" /></a><p class="wp-caption-text">Java execution times for matrix multiplication</p></div> <p>You should definitely know if some Java-datastructures are synchronised or not. And you should know how the computer / caches work.</p> <h2>C++</h2> <p>I have gcc 4.4.3 and compiled everything with these options:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">g++ -std<span class="o">=</span>c++98 -Wall -O3 -g myScript.cpp -o <span class="nv">$`</span><span class="o">(</span>PROBLEM<span class="o">)</span>.out -pedantic</code></pre></div> <h3>ijk-algorithm</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;sstream&gt;</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;fstream&gt;</span> <span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">Result</span> <span class="p">{</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">B</span><span class="p">;</span> <span class="p">};</span> <span class="n">Result</span> <span class="nf">read</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">)</span> <span class="p">{</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">;</span> <span class="n">Result</span> <span class="n">ab</span><span class="p">;</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="n">ifstream</span> <span class="n">infile</span><span class="p">;</span> <span class="n">infile</span><span class="p">.</span><span class="n">open</span> <span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">());</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">)</span> <span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span><span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="o">!</span><span class="n">line</span><span class="p">.</span><span class="n">empty</span><span class="p">())</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">A</span><span class="p">.</span><span class="n">resize</span><span class="p">(</span><span class="n">A</span><span class="p">.</span><span class="n">size</span><span class="p">()</span> <span class="o">+</span> <span class="mi">1</span><span class="p">);</span> <span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">push_back</span><span class="p">(</span><span class="n">a</span><span class="p">);</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">))</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">B</span><span class="p">.</span><span class="n">resize</span><span class="p">(</span><span class="n">B</span><span class="p">.</span><span class="n">size</span><span class="p">()</span> <span class="o">+</span> <span class="mi">1</span><span class="p">);</span> <span class="kt">int</span> <span class="n">a</span><span class="p">;</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">B</span><span class="p">[</span><span class="n">i</span><span class="p">].</span><span class="n">push_back</span><span class="p">(</span><span class="n">a</span><span class="p">);</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">infile</span><span class="p">.</span><span class="n">close</span><span class="p">();</span> <span class="n">ab</span><span class="p">.</span><span class="n">A</span> <span class="o">=</span> <span class="n">A</span><span class="p">;</span> <span class="n">ab</span><span class="p">.</span><span class="n">B</span> <span class="o">=</span> <span class="n">B</span><span class="p">;</span> <span class="k">return</span> <span class="n">ab</span><span class="p">;</span> <span class="p">}</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">ijkalgorithm</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">A</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">B</span><span class="p">)</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">A</span><span class="p">.</span><span class="n">size</span><span class="p">();</span> <span class="c1">// initialise C with 0s</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">tmp</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="mi">0</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">C</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">tmp</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">];</span> <span class="p">}</span> <span class="p">}</span> <span class="p">}</span> <span class="k">return</span> <span class="n">C</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">matrix</span><span class="p">)</span> <span class="p">{</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">it</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">inner</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="n">it</span><span class="o">=</span><span class="n">matrix</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">it</span> <span class="o">!=</span> <span class="n">matrix</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="n">it</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="n">inner</span> <span class="o">=</span> <span class="n">it</span><span class="o">-&gt;</span><span class="n">begin</span><span class="p">();</span> <span class="n">inner</span> <span class="o">!=</span> <span class="n">it</span><span class="o">-&gt;</span><span class="n">end</span><span class="p">();</span> <span class="n">inner</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="o">*</span><span class="n">inner</span><span class="p">;</span> <span class="k">if</span><span class="p">(</span><span class="n">inner</span><span class="o">+</span><span class="mi">1</span> <span class="o">!=</span> <span class="n">it</span><span class="o">-&gt;</span><span class="n">end</span><span class="p">())</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="kt">int</span> <span class="n">main</span> <span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="n">string</span> <span class="n">filename</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">&lt;</span> <span class="mi">3</span><span class="p">)</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;2000.in&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">argv</span><span class="p">[</span><span class="mi">2</span><span class="p">];</span> <span class="p">}</span> <span class="n">Result</span> <span class="n">result</span> <span class="o">=</span> <span class="n">read</span> <span class="p">(</span><span class="n">filename</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">C</span> <span class="o">=</span> <span class="n">ijkalgorithm</span><span class="p">(</span><span class="n">result</span><span class="p">.</span><span class="n">A</span><span class="p">,</span> <span class="n">result</span><span class="p">.</span><span class="n">B</span><span class="p">);</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 1m40.439s user 1m38.642s sys 0m0.280s</code></pre></div> <h3>ikj-algorithm</h3> <p>Again, I’ve only switched line 61 and 62.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 0m15.172s user 0m14.877s sys 0m0.248s</code></pre></div> <h3>Library: Boost</h3> <p>If you want to compile these scripts, you might have to install the boost libraries first. On Ubuntu you can enter:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install libboost-math*</code></pre></div> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;sstream&gt;</span> <span class="cp">#include &lt;string&gt;</span> <span class="cp">#include &lt;fstream&gt;</span> <span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="cp">#include &lt;boost/numeric/ublas/matrix.hpp&gt;</span> <span class="cp">#include &lt;boost/numeric/ublas/io.hpp&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="k">struct</span> <span class="n">Result</span> <span class="p">{</span> <span class="n">boost</span><span class="o">::</span><span class="n">numeric</span><span class="o">::</span><span class="n">ublas</span><span class="o">::</span><span class="n">matrix</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">A</span><span class="p">;</span> <span class="n">boost</span><span class="o">::</span><span class="n">numeric</span><span class="o">::</span><span class="n">ublas</span><span class="o">::</span><span class="n">matrix</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">B</span><span class="p">;</span> <span class="p">};</span> <span class="kt">int</span> <span class="nf">getMatrixSize</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">)</span> <span class="p">{</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="n">ifstream</span> <span class="n">infile</span><span class="p">;</span> <span class="n">infile</span><span class="p">.</span><span class="n">open</span> <span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">());</span> <span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">);</span> <span class="k">return</span> <span class="n">count</span><span class="p">(</span><span class="n">line</span><span class="p">.</span><span class="n">begin</span><span class="p">(),</span> <span class="n">line</span><span class="p">.</span><span class="n">end</span><span class="p">(),</span> <span class="sc">&#39;\t&#39;</span><span class="p">)</span> <span class="o">+</span> <span class="mi">1</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">printMatrix</span><span class="p">(</span><span class="n">boost</span><span class="o">::</span><span class="n">numeric</span><span class="o">::</span><span class="n">ublas</span><span class="o">::</span><span class="n">matrix</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">matrix</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">matrix</span><span class="p">.</span><span class="n">size1</span><span class="p">();</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="n">matrix</span><span class="p">.</span><span class="n">size2</span><span class="p">();</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">matrix</span><span class="p">(</span><span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">);</span> <span class="k">if</span><span class="p">(</span><span class="n">j</span><span class="o">+</span><span class="mi">1</span> <span class="o">!=</span> <span class="n">matrix</span><span class="p">.</span><span class="n">size2</span><span class="p">())</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;</span><span class="se">\t</span><span class="s">&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">Result</span> <span class="nf">read</span><span class="p">(</span><span class="n">string</span> <span class="n">filename</span><span class="p">)</span> <span class="p">{</span> <span class="n">Result</span> <span class="n">ab</span><span class="p">;</span> <span class="n">string</span> <span class="n">line</span><span class="p">;</span> <span class="n">ifstream</span> <span class="n">infile</span><span class="p">;</span> <span class="n">infile</span><span class="p">.</span><span class="n">open</span> <span class="p">(</span><span class="n">filename</span><span class="p">.</span><span class="n">c_str</span><span class="p">());</span> <span class="c1">// get dimension</span> <span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">);</span> <span class="kt">int</span> <span class="n">n</span> <span class="o">=</span> <span class="n">getMatrixSize</span><span class="p">(</span><span class="n">filename</span><span class="p">);</span> <span class="n">boost</span><span class="o">::</span><span class="n">numeric</span><span class="o">::</span><span class="n">ublas</span><span class="o">::</span><span class="n">matrix</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">A</span><span class="p">(</span><span class="n">n</span><span class="p">,</span><span class="n">n</span><span class="p">),</span> <span class="n">B</span><span class="p">(</span><span class="n">n</span><span class="p">,</span><span class="n">n</span><span class="p">);</span> <span class="c1">// process first line</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="kt">int</span> <span class="n">a</span><span class="p">,</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">(</span><span class="n">i</span><span class="p">,</span><span class="n">j</span><span class="p">)</span> <span class="o">=</span> <span class="n">a</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">)</span> <span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span><span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="o">!</span><span class="n">line</span><span class="p">.</span><span class="n">empty</span><span class="p">())</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">A</span><span class="p">(</span><span class="n">i</span><span class="p">,</span><span class="n">j</span><span class="p">)</span> <span class="o">=</span> <span class="n">a</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">getline</span><span class="p">(</span><span class="n">infile</span><span class="p">,</span> <span class="n">line</span><span class="p">))</span> <span class="p">{</span> <span class="n">istringstream</span> <span class="n">iss</span><span class="p">(</span><span class="n">line</span><span class="p">);</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">while</span> <span class="p">(</span><span class="n">iss</span> <span class="o">&gt;&gt;</span> <span class="n">a</span><span class="p">)</span> <span class="p">{</span> <span class="n">B</span><span class="p">(</span><span class="n">i</span><span class="p">,</span><span class="n">j</span><span class="p">)</span> <span class="o">=</span> <span class="n">a</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">i</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="n">infile</span><span class="p">.</span><span class="n">close</span><span class="p">();</span> <span class="n">ab</span><span class="p">.</span><span class="n">A</span> <span class="o">=</span> <span class="n">A</span><span class="p">;</span> <span class="n">ab</span><span class="p">.</span><span class="n">B</span> <span class="o">=</span> <span class="n">B</span><span class="p">;</span> <span class="k">return</span> <span class="n">ab</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span> <span class="p">(</span><span class="kt">int</span> <span class="n">argc</span><span class="p">,</span> <span class="kt">char</span><span class="o">*</span> <span class="n">argv</span><span class="p">[])</span> <span class="p">{</span> <span class="n">string</span> <span class="n">filename</span><span class="p">;</span> <span class="k">if</span> <span class="p">(</span><span class="n">argc</span> <span class="o">&lt;</span> <span class="mi">3</span><span class="p">)</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="s">&quot;2000.in&quot;</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">filename</span> <span class="o">=</span> <span class="n">argv</span><span class="p">[</span><span class="mi">2</span><span class="p">];</span> <span class="p">}</span> <span class="n">Result</span> <span class="n">result</span> <span class="o">=</span> <span class="n">read</span> <span class="p">(</span><span class="n">filename</span><span class="p">);</span> <span class="n">boost</span><span class="o">::</span><span class="n">numeric</span><span class="o">::</span><span class="n">ublas</span><span class="o">::</span><span class="n">matrix</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">C</span><span class="p">;</span> <span class="n">C</span> <span class="o">=</span> <span class="n">boost</span><span class="o">::</span><span class="n">numeric</span><span class="o">::</span><span class="n">ublas</span><span class="o">::</span><span class="n">prod</span><span class="p">(</span><span class="n">result</span><span class="p">.</span><span class="n">A</span><span class="p">,</span> <span class="n">result</span><span class="p">.</span><span class="n">B</span><span class="p">);</span> <span class="n">printMatrix</span><span class="p">(</span><span class="n">C</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">real 4m15.388s user 4m10.272s sys 0m0.588s</code></pre></div> <h3>Library: Blitz</h3> <p>This is a great example of useless library. I’ve installed the library:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install libblitz*</code></pre></div> <p>Then I wanted to use it. Well, I have no clue how I could exactly use it! See my StackOverflow Question: <a href="http://stackoverflow.com/questions/11113993/is-a-documentation-of-blitz-matrices-available">Is a documentation of Blitz++ matrices available?</a></p> <h3>Conclusion for C++</h3> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/06/cpp-execution-time.png"><img src="../images/2012/06/cpp-execution-time.png" alt="C++ execution times for matrix multiplication" width="" height="" class="size-full wp-image-28351" /></a><p class="wp-caption-text">C++ execution times for matrix multiplication</p></div> <p>Again, it brings a performance boost if you know how your CPU works. I was very astonished, that the library Boost is slower (actually MUCH slower) than my simplest approach was.</p> <h2>Conclusion</h2> <p>If I want to create a working piece of code in a minimum amount of time, I will always take Python. It has been very easy to solve this task with the given restrictions. But C++ is amazing when speed is important.</p> <p>It was astonishingly difficult to find working code examples for this task for Java and C++. I was searching for libraries and found some, but the search results were not satisfying.</p> <h2>See also</h2> <ul> <li><a href="http://www.boost.org/doc/libs/1_49_0/libs/numeric/ublas/doc/matrix.htm">Boost Matrix multiplication</a></li> <li><a href="http://rosettacode.org/wiki/Matrix_multiplication">Rosetta Code: Matrix multiplication</a> (Implementations in 63 programming languages!)</li> <li><a href="http://stackoverflow.com/questions/10442365/why-is-matrix-multiplication-faster-with-numpy-than-with-ctypes-in-python">Why is matrix multiplication faster with numpy than with ctypes in Python?</a></li> <li><a href="http://stackoverflow.com/questions/11110604/why-is-boosts-matrix-multiplication-slower-than-mine">Why is boosts matrix multiplication slower than mine?</a></li> </ul> <div class="info">Continue reading with Part II: <a href="../strassen-algorithm-in-python-java-cpp/">The Strassen algorithm in Python, Java and C++</a></div> Python Puzzle #1: List multiplication //martin-thoma.com/python-puzzle-1-list-multiplication/ Mon, 18 Jun 2012 15:06:48 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-puzzle-1-list-multiplication <h2>Basic concepts</h2> <p>Image you had to multiply two small matrices in Python. You could just use the definition of a matrix product:</p> <p><code>$A, B \in \mathbb{R}^{n \times n}$</code>: <code>$C = A \cdot B, C \in \mathbb{R}^{n \times n}$</code> where the components of C are definied by <code>$c_{i,j} = \sum_{k=1}^n a_{i,k} \cdot b_{k, j}$</code></p> <p>Note that this means: <code>$\begin{pmatrix} 1 &amp; 2 \\ 3 &amp; 4 \end{pmatrix} \cdot \begin{pmatrix} 5 &amp; 6 \\ 7 &amp; 8 \end{pmatrix} = \begin{pmatrix} 19 &amp; 22 \\ 43 &amp; 50 \end{pmatrix}$</code></p> <p>You might also have heard of Pythons overloaded multiplication:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">print</span><span class="p">([</span><span class="mi">0</span><span class="p">]</span><span class="o">*</span><span class="mi">4</span><span class="p">)</span> <span class="k">print</span><span class="p">([[</span><span class="mi">0</span><span class="p">]</span><span class="o">*</span><span class="mi">4</span><span class="p">]</span><span class="o">*</span><span class="mi">4</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;abc&quot;</span><span class="o">*</span><span class="mi">4</span><span class="p">)</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">[0, 0, 0, 0] [[0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0], [0, 0, 0, 0]] abcabcabcabc</code></pre></div> <h2>Question</h2> <p>What do you think does the following piece of Python-Code print?</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">standardMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span><span class="p">]</span><span class="o">*</span><span class="n">n</span><span class="p">]</span><span class="o">*</span><span class="n">n</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span> <span class="n">A</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">2</span><span class="p">],</span> <span class="p">[</span><span class="mi">3</span><span class="p">,</span><span class="mi">4</span><span class="p">]]</span> <span class="n">B</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">5</span><span class="p">,</span><span class="mi">6</span><span class="p">],</span> <span class="p">[</span><span class="mi">7</span><span class="p">,</span><span class="mi">8</span><span class="p">]]</span> <span class="k">print</span> <span class="n">standardMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">)</span></code></pre></div> <p>. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .</p> <h2>Answer</h2> <div class="highlight"><pre><code class="language-text" data-lang="text">[[32, 32], [32, 32]]</code></pre></div> <p>Python creates only one list and makes pointers to it!</p> <p>So this is one that works:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">standardMatrixProduct</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">n</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">C</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">0</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">)]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="k">print</span> <span class="n">C</span> <span class="n">C</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">+=</span> <span class="n">A</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">k</span><span class="p">]</span> <span class="o">*</span> <span class="n">B</span><span class="p">[</span><span class="n">k</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="k">return</span> <span class="n">C</span></code></pre></div> Duolingo - Learn a Language Online //martin-thoma.com/duolingo-learn-language-online/ Sun, 17 Jun 2012 12:02:19 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/duolingo-learn-language-online <p><a href="http://duolingo.com/">Duolingo</a> is a great online protal for learning new languages online. They currently support German, Spanish, French, Portuguese, Italian and Chinese.</p> <p>Here is a short explanation of Duolingo:</p> <iframe width="512" height="288" src="http://www.youtube.com/embed/WyzJ2Qq9Abs" frameborder="0" allowfullscreen=""></iframe> <p>The inventor of duolingo, Luis von Ahn, did also a great TED-Talk in which he explains the concepts:</p> <object width="526" height="374"> <param name="movie" value="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" /> <param name="allowFullScreen" value="true" /> <param name="allowScriptAccess" value="always" /> <param name="wmode" value="transparent" /> <param name="bgColor" value="#ffffff" /> <param name="flashvars" value="vu=http://video.ted.com/talk/stream/2011X/Blank/LuisVonAhn_2011X-320k.mp4&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/LuisVonAhn_2011X-embed.jpg&amp;vw=512&amp;vh=288&amp;ap=0&amp;ti=1295&amp;lang=&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=luis_von_ahn_massive_scale_online_collaboration;year=2011;theme=the_rise_of_collaboration;event=TEDxCMU;tag=Internet;tag=collaboration;tag=computers;tag=language;tag=technology;&amp;preAdTag=tconf.ted/embed;tile=1;sz=512x288;" /> <embed src="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" pluginspace="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" wmode="transparent" bgcolor="#ffffff" width="526" height="374" allowfullscreen="true" allowscriptaccess="always" flashvars="vu=http://video.ted.com/talk/stream/2011X/Blank/LuisVonAhn_2011X-320k.mp4&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/LuisVonAhn_2011X-embed.jpg&amp;vw=512&amp;vh=288&amp;ap=0&amp;ti=1295&amp;lang=&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=luis_von_ahn_massive_scale_online_collaboration;year=2011;theme=the_rise_of_collaboration;event=TEDxCMU;tag=Internet;tag=collaboration;tag=computers;tag=language;tag=technology;&amp;preAdTag=tconf.ted/embed;tile=1;sz=512x288;" /> </object> <p>Now some screenshots to give you a feeling what Duolingo offers:</p> <div style="width: 498px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-advancement.png"><img src="../images/2012/06/duolingo-advancement.png" alt="Achievements in Duolingo" width="" height="" class="size-full wp-image-27071" /></a><p class="wp-caption-text">Achievements in Duolingo</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-translation-300x155.png"><img src="../images/2012/06/duolingo-translation-300x155.png" alt="Translation in Duolingo" width="" height="" class="size-medium wp-image-27081" /></a><p class="wp-caption-text">Translation in Duolingo</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-typo-300x166.png"><img src="../images/2012/06/duolingo-typo-300x166.png" alt="Duolingo analyses your errors." width="" height="" class="size-medium wp-image-27091" /></a><p class="wp-caption-text">Duolingo analyses your errors.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-speech-300x149.png"><img src="../images/2012/06/duolingo-speech-300x149.png" alt="Speech to text task in Duolingo" width="" height="" class="size-medium wp-image-27101" /></a><p class="wp-caption-text">Speech to text task in Duolingo</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-photo-to-language-300x167.png"><img src="../images/2012/06/duolingo-photo-to-language-300x167.png" alt="Duolingo: Photo to language" width="" height="" class="size-medium wp-image-27111" /></a><p class="wp-caption-text">Duolingo: Photo to language</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-multiple-choice-300x137.png"><img src="../images/2012/06/duolingo-multiple-choice-300x137.png" alt="Multiple choice in Duolingo" width="" height="" class="size-medium wp-image-27121" /></a><p class="wp-caption-text">Multiple choice in Duolingo</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-lection-300x173.png"><img src="../images/2012/06/duolingo-lection-300x173.png" alt="A lection in Duolingo" width="" height="" class="size-medium wp-image-27131" /></a><p class="wp-caption-text">A lection in Duolingo</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/06/duolingo-achivement-300x138.png"><img src="../images/2012/06/duolingo-achivement-300x138.png" alt="Level mastered ☺" width="" height="" class="size-medium wp-image-27141" /></a><p class="wp-caption-text">Level mastered ☺</p></div> <p>I have 3 invitations left. If you like to test Duolingo, simply post a comment with your email-address. The first three will get the invitations.</p> How to print MIPS assembly code in LaTeX //martin-thoma.com/how-print-mips-assembly-code-latex/ Sat, 16 Jun 2012 11:33:11 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-print-mips-assembly-code-latex <p>If you like to print highlighted MIPS assembly code in LaTeX, you can use the listings package. Sadly, no MIPS language file exits by default in LaTeX, but awg has created one and provides it on his blog. Just download <a href="../images/2012/06/mips.sty_.zip">mips.sty</a> (thanks to <a href="http://blog.xvx.ca/typesetting-mips-assembly-with-latex">Adam Gordon</a>!) and place it in your project folder. Then you can create a project like this:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/06/mips-latex-highlight.png"><img src="../images/2012/06/mips-latex-highlight.png" alt="Highlight MIPS Assembly code with LaTeX listings." width="" height="" class="size-full wp-image-26981" /></a><p class="wp-caption-text">Highlight MIPS Assembly code with LaTeX listings.</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage[margin=2.5cm]{geometry} %layout \usepackage{listings} % needed for the inclusion of source code \usepackage{mips} % the following is needed for syntax highlighting \usepackage{color} \definecolor{dkgreen}{rgb}{0,0.6,0} \definecolor{gray}{rgb}{0.5,0.5,0.5} \definecolor{mauve}{rgb}{0.58,0,0.82} \lstset{ % language=[mips]Assembler, % the language of the code basicstyle=\footnotesize, % the size of the fonts that are used for the code numbers=left, % where to put the line-numbers numberstyle=\tiny\color{gray}, % the style that is used for the line-numbers stepnumber=1, % the step between two line-numbers. If it's 1, each line % will be numbered numbersep=5pt, % how far the line-numbers are from the code backgroundcolor=\color{white}, % choose the background color. You must add \usepackage{color} showspaces=false, % show spaces adding particular underscores showstringspaces=false, % underline spaces within strings showtabs=false, % show tabs within strings adding particular underscores frame=single, % adds a frame around the code rulecolor=\color{black}, % if not set, the frame-color may be changed on line-breaks within not-black text (e.g. commens (green here)) tabsize=4, % sets default tabsize to 2 spaces captionpos=b, % sets the caption-position to bottom breaklines=true, % sets automatic line breaking breakatwhitespace=false, % sets if automatic breaks should only happen at whitespace title=\lstname, % show the filename of files included with \lstinputlisting; % also try caption instead of title keywordstyle=\color{blue}, % keyword style commentstyle=\color{dkgreen}, % comment style stringstyle=\color{mauve}, % string literal style escapeinside={\%*}{*)}, % if you want to add a comment within your code morekeywords={*,...} % if you want to add more keywords to the set } % this is needed for forms and links within the text \usepackage{hyperref} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % Variablen % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \newcommand{\authorName}{Martin Thoma} \newcommand{\tags}{\authorName, my, tags} \title{Aufgabe 5} \author{\authorName} \date{\today} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % PDF Meta information % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \hypersetup{ pdfauthor = {\authorName}, pdfkeywords = {\tags}, pdftitle = {This is the title} } %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % THE DOCUMENT BEGINS % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \begin{document} \lstinputlisting{aufgabe-5.s} \end{document} </pre></div> </div> </div> <h2>See also</h2> <ul> <li><a href="../how-to-print-source-code-with-latex/" title="How to print Source Code with LaTeX">How to print Source Code with LaTeX"</a></li> <li><a href="http://blog.xvx.ca/typesetting-mips-assembly-with-latex">Typesetting MIPS Assembly Code in LaTeX</a></li> <li><a href="../add-mips-syntax-highlighting-gedit/" title="Add MIPS syntax highlighting to gEdit">Add MIPS syntax highlighting to gEdit</a></li> </ul> Add MIPS syntax highlighting to gEdit //martin-thoma.com/add-mips-syntax-highlighting-gedit/ Sat, 16 Jun 2012 10:27:09 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/add-mips-syntax-highlighting-gedit <p>I have to code some little programs in MIPS assembly language for university. So I liked to have some syntax highlighting for my favorite editor: gEdit.</p> <p>The following steps were tested on Ubuntu 10.04.4 LTS.</p> <p>This adds MIPS syntax highlighting to gEdit and every editor, that uses gtksourceview.</p> <p>Create the following file: <code>/usr/share/gtksourceview-2.0/language-specs/sal.lang</code></p> <p>Source: GITHub: <a href="https://github.com/Xodarap/Mips-Assembly-Syntax-Highlighting">Xodarap / Mips-Assembly-Syntax-Highlighting</a></p> <p>Copy and paste the following:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#579">&lt;?xml version=&quot;1.0&quot; encoding=&quot;UTF-8&quot;?&gt;</span> <span style="color:#777">&lt;!-- Author: Ben West Copyright (C) 2010 Ben West edited by Martin Thoma This library is free software; you can redistribute it and/or modify it under the terms of the GNU Library General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for more details. You should have received a copy of the GNU Library General Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. --&gt;</span> <span style="color:#777">&lt;!-- Somewhat copied and pasted from nasm.lang --&gt;</span> <span style="color:#070;font-weight:bold">&lt;language</span> <span style="color:#b48">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">mal</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">MAL</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">version</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">2.0</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">_section</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Others</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span> <span style="color:#070;font-weight:bold">&lt;metadata&gt;</span> <span style="color:#070;font-weight:bold">&lt;property</span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">mimetypes</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>text/mal<span style="color:#070;font-weight:bold">&lt;/property&gt;</span> <span style="color:#070;font-weight:bold">&lt;property</span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">globs</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>*.s<span style="color:#070;font-weight:bold">&lt;/property&gt;</span> <span style="color:#070;font-weight:bold">&lt;property</span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">line-comment-start</span><span style="color:#710">&quot;</span></span><span style="color:#070;font-weight:bold">&gt;</span>#<span style="color:#070;font-weight:bold">&lt;/property&gt;</span> <span style="color:#070;font-weight:bold">&lt;/metadata&gt;</span> <span style="color:#070;font-weight:bold">&lt;style</span><span style="color:#b48">s</span><span style="color:#070;font-weight:bold">&gt;</span> <span style="background-color:hsla(0,0%,0%,0.07);color:black"> <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">comment</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Comment</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:comment</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">error</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Error</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:error</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">string</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">String</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:string</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessor</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Preprocessor</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:preprocessor</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">opcode</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Opcode</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:keyword</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">register</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Register</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:special-char</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">type</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Data Type</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:type</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">escaped-character</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Escaped Character</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:special-char</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">decimal</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Decimal number</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:decimal</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hexadecimal</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Hexadecimal number</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:base-n-integer</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">style</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">label</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">_name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Label</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">map-to</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:identifier</span><span style="color:#710">&quot;</span></span> /&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">styles</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">default-regex-options</span> <span style="color:#070;font-weight:bold">case-sensitive</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">definitions</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">define-regex</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">escaped-character</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">extended</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">\</span><span style="color:#F00;background-color:#FAA">\</span>( <span style="color:#F00;background-color:#FAA">#</span> <span style="color:#070;font-weight:bold">leading</span> <span style="color:#070;font-weight:bold">backslash</span> [<span style="color:#b48">\\\&quot;\'</span>] <span style="color:#F00;background-color:#FAA">#</span> <span style="color:#070;font-weight:bold">escaped</span> <span style="color:#070;font-weight:bold">character</span> ) <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">define-regex</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">mal</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessor</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">preprocessor</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">prefix</span>&gt;<span style="color:#F00;background-color:#FAA">^</span><span style="color:#F00;background-color:#FAA">\</span>.<span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">prefix</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">data</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">text</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">comment</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">comment</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">end-at-line-end</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">start</span>&gt;<span style="color:#F00;background-color:#FAA">#</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">start</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">def:in-line-comment</span><span style="color:#710">&quot;</span></span>/&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">string</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">string</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">end-at-line-end</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">start</span>&gt;<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">&lt;/start</span><span style="color:#710">&gt;</span></span> <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">end</span>&gt;<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">&lt;/end</span><span style="color:#710">&gt;</span></span> <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">escaped-characterw</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">escaped-character</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">match</span>&gt;<span style="color:#F00;background-color:#FAA">\</span><span style="color:#F00;background-color:#FAA">%</span>{<span style="color:#606">escaped-character</span>}<span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">match</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">string2</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">string</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">end-at-line-end</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">start</span>&gt;<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&lt;/start</span><span style="color:#710">&gt;</span></span> <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">end</span>&gt;<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">&lt;/end</span><span style="color:#710">&gt;</span></span> <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">escaped-characters</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">escaped-character</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">match</span>&gt;<span style="color:#F00;background-color:#FAA">\</span><span style="color:#F00;background-color:#FAA">%</span>{<span style="color:#606">escaped-character</span>}<span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">match</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hexadecimal-number</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">hexadecimal</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">match</span> <span style="color:#070;font-weight:bold">extended</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; (<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">&amp;</span><span style="color:#070;font-weight:bold">amp</span>;<span style="color:#070;font-weight:bold">lt</span>;<span style="color:#F00;background-color:#FAA">!</span>[<span style="color:#b48">\w\.</span>]) [<span style="color:#b48">+-</span>]<span style="color:#F00;background-color:#FAA">?</span><span style="color:#60E">0</span><span style="color:#070;font-weight:bold">x</span>[<span style="color:#b48">0-9a-fA-F</span>]+ (<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">!</span>[<span style="color:#b48">\w\.</span>]) <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">match</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">decimal</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">decimal</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">match</span> <span style="color:#070;font-weight:bold">extended</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; (<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">&amp;</span><span style="color:#070;font-weight:bold">amp</span>;<span style="color:#070;font-weight:bold">lt</span>;<span style="color:#F00;background-color:#FAA">!</span>[<span style="color:#b48">\w\.</span>]) [<span style="color:#b48">0-9</span>]+ (<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">!</span>[<span style="color:#b48">\w\.</span>]) <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">match</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">registers</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">register</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">match</span> <span style="color:#070;font-weight:bold">extended</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; (<span style="color:#F00;background-color:#FAA">\</span><span style="color:#F00;background-color:#FAA">$</span> ( <span style="color:#F00;background-color:#FAA">\</span><span style="color:#070;font-weight:bold">d</span><span style="color:#F00;background-color:#FAA">|</span>[<span style="color:#b48">12</span>]<span style="color:#F00;background-color:#FAA">\</span><span style="color:#070;font-weight:bold">d</span><span style="color:#F00;background-color:#FAA">|</span><span style="color:#60E">3</span>[<span style="color:#b48">12</span>]<span style="color:#F00;background-color:#FAA">|</span> (<span style="color:#070;font-weight:bold">ra</span>)<span style="color:#F00;background-color:#FAA">|</span> ([<span style="color:#b48">vk</span>][<span style="color:#b48">01</span>])<span style="color:#F00;background-color:#FAA">|</span> (<span style="color:#070;font-weight:bold">a</span>[<span style="color:#b48">0-3t</span>])<span style="color:#F00;background-color:#FAA">|</span> (<span style="color:#070;font-weight:bold">t</span>[<span style="color:#b48">0-9</span>])<span style="color:#F00;background-color:#FAA">|</span> (<span style="color:#070;font-weight:bold">s</span>[<span style="color:#b48">0-7p</span>])<span style="color:#F00;background-color:#FAA">|</span> ([<span style="color:#b48">gsf</span>]<span style="color:#070;font-weight:bold">p</span>)<span style="color:#F00;background-color:#FAA">|</span> (<span style="color:#070;font-weight:bold">zero</span>) ) )<span style="color:#F00;background-color:#FAA">\</span><span style="color:#070;font-weight:bold">b</span> <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">match</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">label</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">label</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">match</span> <span style="color:#070;font-weight:bold">extended</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">^</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#070;font-weight:bold">w</span>+: <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">match</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#F00;background-color:#FAA">!</span><span style="color:#F00;background-color:#FAA">-</span><span style="color:#F00;background-color:#FAA">-</span> <span style="color:#070;font-weight:bold">Opcodes</span> <span style="color:#F00;background-color:#FAA">-</span><span style="color:#F00;background-color:#FAA">-</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">opcodes_simple</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">opcode</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#F00;background-color:#FAA">!</span><span style="color:#F00;background-color:#FAA">-</span><span style="color:#F00;background-color:#FAA">-</span> <span style="color:#070;font-weight:bold">MAL</span> <span style="color:#070;font-weight:bold">Opcodes</span> <span style="color:#F00;background-color:#FAA">-</span><span style="color:#F00;background-color:#FAA">-</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">la</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">li</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">lw</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">lb</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">lbu</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">sw</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">sb</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#F00;background-color:#FAA">a</span><span style="color:#F00;background-color:#FAA">d</span><span style="color:#F00;background-color:#FAA">d</span>(<span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span>)<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#F00;background-color:#FAA">s</span><span style="color:#F00;background-color:#FAA">u</span><span style="color:#F00;background-color:#FAA">b</span>(<span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span>)<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#F00;background-color:#FAA">m</span><span style="color:#F00;background-color:#FAA">u</span><span style="color:#F00;background-color:#FAA">l</span>(<span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span>)<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#F00;background-color:#FAA">d</span><span style="color:#F00;background-color:#FAA">i</span><span style="color:#F00;background-color:#FAA">v</span>(<span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span>)<span style="color:#F00;background-color:#FAA">?</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">rem</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">and</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">or</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">xor</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">nor</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">not</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">move</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">sll</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">srl</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">sra</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">l</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">s</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">mov</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">cvt</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.w</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">cvt</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.w</span><span style="color:#F00;background-color:#FAA">\</span><span style="color:#B06;font-weight:bold">.s</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">mfc0</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">mtc0</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">mfc1</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">mtc1</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">b</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">beq</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bne</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">blt</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bgt</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">ble</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bge</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bltz</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bgtz</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">blez</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bgez</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">bnez</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">beqz</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">j</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">jr</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">jal</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">jalr</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">getc</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">putc</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">puts</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">done</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">syscall</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">andi</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">context</span> <span style="color:#070;font-weight:bold">id</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">types</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">style-ref</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">type</span><span style="color:#710">&quot;</span></span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">prefix</span>&gt;<span style="color:#F00;background-color:#FAA">\</span>.<span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">prefix</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">byte</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">word</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">asciiz</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">ascii</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span><span style="color:#070;font-weight:bold">keyword</span>&gt;<span style="color:#070;font-weight:bold">float</span><span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">keyword</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">include</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">context</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">definitions</span>&gt; <span style="color:#F00;background-color:#FAA">&lt;</span>/<span style="color:#070;font-weight:bold">language</span>&gt; </span></pre></div> </div> </div> <p>That’s it.</p> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/MIPS_architecture">MIPS architecture</a></li> <li>Wikibooks: <a href="http://en.wikibooks.org/wiki/MIPS_Assembly">MIPS Assembly</a></li> <li><a href="http://spimsimulator.sourceforge.net/">SPIM</a> (a MIPS simulator)</li> </ul> Python one-liners for Project Euler //martin-thoma.com/python-one-liners-for-project-euler/ Wed, 13 Jun 2012 17:00:14 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-one-liners-for-project-euler <p>Today, I’ve been trying to get used to <a href="../functional-programming-in-python/" title="Functional Programming in Python">Pythons functional programming tools</a> by solving <a href="http://projecteuler.net/about">Project-Euler</a> tasks. To make them more interesting, I’ve solved them in one line. But I realized, that it is difficult to read online as only about 70 characters get displayed without a scrollbar. So I made multi-line solutions out of them.</p> <p>These snippets are also good examples what’s possible to do with Python and to show that Python is fast.</p> <h2>Problem 24</h2> <blockquote>What is the millionth lexicographic permutation of the digits 0, 1, 2, 3, 4, 5, 6, 7, 8 and 9?</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">from</span> <span class="nn">itertools</span> <span class="kn">import</span> <span class="n">permutations</span><span class="p">,</span> <span class="n">islice</span> <span class="k">print</span> <span class="nb">next</span><span class="p">(</span><span class="n">islice</span><span class="p">(</span><span class="n">permutations</span><span class="p">(</span><span class="s">&quot;0123456789&quot;</span><span class="p">),</span> <span class="mi">999999</span><span class="p">,</span> <span class="mi">999999</span> <span class="o">+</span> <span class="mi">1</span><span class="p">))</span></code></pre></div> <h2>Problem 29</h2> <blockquote>How many distinct terms are in the sequence generated by `$a^b$` for `$2 \leq a \leq 100$` and `$2 \leq b \leq 100$`?</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">d</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">top</span><span class="p">:</span> <span class="nb">len</span><span class="p">(</span><span class="nb">set</span><span class="p">([</span><span class="n">a</span><span class="o">**</span><span class="n">b</span> <span class="k">for</span> <span class="n">a</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span><span class="n">top</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="k">for</span> <span class="n">b</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">top</span><span class="o">+</span><span class="mi">1</span><span class="p">)]))</span></code></pre></div> <h2>Problem 34</h2> <blockquote>145 is a curious number, as 1! + 4! + 5! = 1 + 24 + 120 = 145. Find the sum of all numbers which are equal to the sum of the factorial of their digits. Note: as 1! = 1 and 2! = 2 are not sums they are not included.</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">factorial</span> <span class="n">l</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">:</span> <span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="o">+</span> <span class="n">factorial</span><span class="p">(</span><span class="nb">int</span><span class="p">(</span><span class="n">y</span><span class="p">)),</span> <span class="p">[</span><span class="n">d</span> <span class="k">for</span> <span class="n">d</span> <span class="ow">in</span> <span class="s">&quot;0&quot;</span> <span class="o">+</span> <span class="nb">str</span><span class="p">(</span><span class="n">n</span><span class="p">)])</span> <span class="k">print</span><span class="p">(</span><span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">+</span><span class="n">y</span><span class="p">,</span> <span class="nb">filter</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="n">x</span> <span class="o">==</span> <span class="n">l</span><span class="p">(</span><span class="n">x</span><span class="p">),</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span> <span class="mi">100000</span><span class="p">))))</span></code></pre></div> <h2>Problem 36</h2> <blockquote>The decimal number, 585 = 10010010012 (binary), is palindromic in both bases. Find the sum of all numbers, less than one million, which are palindromic in base 10 and base 2.</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">palindrom</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="nb">str</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="o">==</span> <span class="nb">str</span><span class="p">(</span><span class="n">x</span><span class="p">)[::</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="ow">and</span> <span class="nb">str</span><span class="p">(</span><span class="nb">bin</span><span class="p">(</span><span class="n">x</span><span class="p">))[</span><span class="mi">2</span><span class="p">:]</span> <span class="o">==</span> <span class="nb">str</span><span class="p">(</span><span class="nb">bin</span><span class="p">(</span><span class="n">x</span><span class="p">))[</span><span class="mi">2</span><span class="p">:][::</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="n">d</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">top</span><span class="p">:</span> <span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">+</span><span class="n">y</span><span class="p">,</span> <span class="nb">filter</span><span class="p">(</span><span class="n">palindrom</span><span class="p">,</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="n">top</span><span class="o">+</span><span class="mi">1</span><span class="p">)))</span></code></pre></div> <h2>Problem 48</h2> <blockquote>The series, `$1^1 + 2^2 + 3^3 + ... + 10^{10} = 10405071317$`. Find the last ten digits of the series, `$1^1 + 2^2 + 3^3 + ... + 1000^{1000}$`.</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">d</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">top</span><span class="p">:</span> <span class="nb">str</span><span class="p">(</span><span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">+</span><span class="n">y</span><span class="p">,</span> <span class="p">[</span><span class="n">i</span><span class="o">**</span><span class="n">i</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">top</span><span class="o">+</span><span class="mi">1</span><span class="p">)]))[</span><span class="o">-</span><span class="mi">10</span><span class="p">:]</span></code></pre></div> <h2>Problem 52</h2> <blockquote>Find the smallest positive integer, x, such that 2x, 3x, 4x, 5x, and 6x, contain the same digits in some order.</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">digits</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">,</span> <span class="n">p</span><span class="p">:</span> <span class="nb">set</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">n</span><span class="o">*</span><span class="n">p</span><span class="p">))</span> <span class="n">d</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">:</span> <span class="nb">all</span><span class="p">(</span><span class="n">digits</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="mi">1</span><span class="p">)</span> <span class="o">==</span> <span class="n">digits</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="mi">7</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="nb">filter</span><span class="p">(</span><span class="n">d</span><span class="p">,</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">1000000</span><span class="p">)))</span></code></pre></div> <h2>Problem 53</h2> <blockquote>How many values of `$\binom{n}{r}$`, for `$1 \leq r \leq n \leq 100$`, exceed one-million?</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">factorial</span> <span class="k">as</span> <span class="n">f</span> <span class="k">print</span><span class="p">(</span><span class="nb">sum</span><span class="p">((</span><span class="n">f</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="o">/</span> <span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">j</span><span class="p">)</span> <span class="o">*</span> <span class="n">f</span><span class="p">(</span><span class="n">i</span><span class="o">-</span><span class="n">j</span><span class="p">)))</span> <span class="o">&gt;</span> <span class="mi">1000000</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">101</span><span class="p">)</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">i</span><span class="p">)))</span></code></pre></div> <h2>Problem 56</h2> <blockquote>Considering natural numbers of the form, `$a^b$`, finding the maximum digital sum.</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">print</span> <span class="nb">max</span><span class="p">([</span><span class="nb">sum</span><span class="p">([</span><span class="nb">int</span><span class="p">(</span><span class="n">c</span><span class="p">)</span> <span class="k">for</span> <span class="n">c</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">a</span><span class="o">**</span><span class="n">b</span><span class="p">)])</span> <span class="k">for</span> <span class="n">a</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">100</span><span class="p">)</span> <span class="k">for</span> <span class="n">b</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">100</span><span class="p">)])</span></code></pre></div> <h2>Problem 97</h2> <blockquote>Find the last ten digits of the non-Mersenne prime: `$28433 \cdot 2^{7830457} + 1$`.</blockquote> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">print</span> <span class="p">(</span><span class="mi">28433</span><span class="o">*</span><span class="p">(</span><span class="mi">2</span><span class="o">**</span><span class="mi">7830457</span><span class="p">)</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span><span class="o">%</span><span class="p">(</span><span class="mi">10</span><span class="o">**</span><span class="mi">10</span><span class="p">)</span></code></pre></div> Functional Programming in Python //martin-thoma.com/functional-programming-in-python/ Tue, 12 Jun 2012 17:00:09 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/functional-programming-in-python <p>Python has a few functional programming tools: Lambda functions and the three higher-order functions map, filter and reduce. I’ll explain them now and I’ll give some usage examples.</p> <h2>lambda</h2> <p>A lambda creates an <a href="http://en.wikipedia.org/wiki/Anonymous_function">anonymous function</a>, that means a function without a name. A lambda may have any number of arguments.</p> <p>Here are some examples for lambdas:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">f</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="n">x</span><span class="o">*</span><span class="n">x</span> <span class="k">print</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="mi">7</span><span class="p">))</span></code></pre></div> <p>Output: 49</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">g</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">:</span> <span class="n">x</span> <span class="o">+</span> <span class="n">y</span><span class="o">*</span><span class="n">y</span> <span class="o">+</span> <span class="nb">abs</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">g</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">1</span><span class="p">),</span> <span class="n">g</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="o">-</span><span class="mi">1</span><span class="p">),</span> <span class="n">g</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">),</span> <span class="n">g</span><span class="p">(</span><span class="mi">10</span><span class="p">,</span> <span class="mi">6</span><span class="p">),</span> <span class="n">g</span><span class="p">(</span><span class="o">-</span><span class="mi">10</span><span class="p">,</span> <span class="mi">6</span><span class="p">))</span></code></pre></div> <p>Output: (3, 3, 1, 56, 36)</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">h</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">myVar</span><span class="p">,</span> <span class="n">anotherVar</span><span class="p">:</span> <span class="nb">set</span><span class="p">([</span><span class="n">myVar</span><span class="p">,</span> <span class="n">anotherVar</span><span class="p">])</span> <span class="k">print</span><span class="p">(</span><span class="n">h</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">),</span> <span class="n">h</span><span class="p">(</span><span class="s">&#39;a&#39;</span><span class="p">,</span> <span class="mi">1</span><span class="p">),</span> <span class="n">h</span><span class="p">(</span><span class="s">&#39;a&#39;</span><span class="p">,</span> <span class="s">&#39;a&#39;</span><span class="p">),</span> <span class="n">h</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">))</span></code></pre></div> <p>Output: (set([1, 2]), set([‘a’, 1]), set([‘a’]), set([1]))</p> <p>Sometimes you would like to get an if-statement in a lambda. So imagine you would like to make a lambda function like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">f</span><span class="p">(</span><span class="n">x</span><span class="p">):</span> <span class="k">if</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="mi">42</span> <span class="k">elif</span> <span class="n">x</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="mi">1337</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="mi">0</span></code></pre></div> <p>This is the way you would do it:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">f</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="n">x</span><span class="o">==</span><span class="mi">0</span> <span class="ow">and</span> <span class="mi">42</span> <span class="ow">or</span> <span class="n">x</span><span class="o">==</span><span class="mi">1</span> <span class="ow">and</span> <span class="mi">1337</span> <span class="ow">or</span> <span class="mi">0</span></code></pre></div> <p>(Thanks to <a href="http://eikke.com/python-ifelse-in-lambda/">Ikke’s blog</a> for the hint!)</p> <h2>map(function, sequence)</h2> <p>Map is a function with two parameters. The first parameter is another function, the second is a sequence. Map returns a list. It only applies function to every item of the sequence.</p> <p>Here are some examples:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">square</span><span class="p">(</span><span class="n">x</span><span class="p">):</span> <span class="k">return</span> <span class="n">x</span><span class="o">*</span><span class="n">x</span> <span class="n">l</span> <span class="o">=</span> <span class="nb">map</span><span class="p">(</span><span class="n">square</span><span class="p">,</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">6</span><span class="p">,</span> <span class="mi">7</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">9</span><span class="p">,</span> <span class="mi">10</span><span class="p">])</span></code></pre></div> <p>l = [1, 4, 9, 16, 25, 36, 49, 64, 81, 100]</p> <p>This is equivalent to:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">l</span> <span class="o">=</span> <span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="n">x</span><span class="o">*</span><span class="n">x</span><span class="p">,</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">11</span><span class="p">))</span></code></pre></div> <p>You can also use more than one list:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">a</span> <span class="o">=</span> <span class="nb">xrange</span><span class="p">(</span><span class="o">-</span><span class="mi">10</span><span class="p">,</span> <span class="mi">10</span><span class="p">)</span> <span class="n">b</span> <span class="o">=</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">20</span><span class="p">)</span> <span class="n">l</span> <span class="o">=</span> <span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">*</span><span class="n">y</span><span class="p">,</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span></code></pre></div> <p>Output: [0, -9, -16, -21, -24, -25, -24, -21, -16, -9, 0, 11, 24, 39, 56, 75, 96, 119, 144, 171]</p> <h2>reduce(function, sequence)</h2> <p>You can quite often reduce problems to an operation on two elements. Reduce takes two elements from sequence, uses function on them and saves the result. Then it takes the result and another element of the sequence and uses function…</p> <p>Example: Imagine you would like to get the sum of a list. Then you need to add two elements of the list, save the result and add another element, save the result, add another element, …</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">r</span> <span class="o">=</span> <span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">+</span><span class="n">y</span><span class="p">,</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span><span class="mi">63</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">5</span><span class="p">])</span></code></pre></div> <p>r = 74</p> <p>You can calculate the factorial n! like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">fac</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">n</span><span class="p">:</span> <span class="nb">reduce</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span><span class="n">x</span><span class="o">*</span><span class="n">y</span><span class="p">,</span><span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">fac</span><span class="p">(</span><span class="mi">2</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">fac</span><span class="p">(</span><span class="mi">3</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">fac</span><span class="p">(</span><span class="mi">10</span><span class="p">))</span></code></pre></div> <p>Output: 2 6 3628800</p> <h2>filter(function, sequence)</h2> <p>filter gets all elements from sequence, where function returns true:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">isPrime</span><span class="p">(</span><span class="n">element</span><span class="p">):</span> <span class="k">if</span> <span class="n">element</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">elif</span> <span class="n">element</span> <span class="o">&lt;=</span> <span class="mi">1</span> <span class="ow">or</span> <span class="n">element</span> <span class="o">%</span> <span class="mi">2</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">else</span><span class="p">:</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span> <span class="n">element</span><span class="p">,</span> <span class="mi">2</span><span class="p">):</span> <span class="k">if</span> <span class="n">element</span> <span class="o">%</span> <span class="n">i</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span> <span class="n">myList</span> <span class="o">=</span> <span class="p">[</span><span class="mi">4</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">9</span><span class="p">,</span> <span class="mi">12</span><span class="p">,</span> <span class="mi">13</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">7</span><span class="p">,</span> <span class="mi">9</span><span class="p">,</span> <span class="mi">11</span><span class="p">,</span> <span class="mi">11</span><span class="p">]</span> <span class="n">r</span> <span class="o">=</span> <span class="nb">filter</span><span class="p">(</span><span class="n">isPrime</span><span class="p">,</span> <span class="n">myList</span><span class="p">)</span></code></pre></div> <p>r = [13, 2, 7, 11, 11]</p> <h2>Some more examples</h2> <p>Task: What is the sum of digits of <code>$2^n, n \in \mathbb{N}$</code>?</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">sumOfDigits</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">exp</span><span class="p">:</span> <span class="nb">reduce</span><span class="p">(</span> <span class="k">lambda</span> <span class="n">x</span><span class="p">,</span><span class="n">y</span><span class="p">:</span> <span class="n">x</span><span class="o">+</span><span class="n">y</span><span class="p">,</span> <span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">),</span> <span class="nb">str</span><span class="p">(</span><span class="mi">2</span><span class="o">**</span><span class="n">exp</span><span class="p">))</span> <span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">sumOfDigits</span><span class="p">(</span><span class="mi">2</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">sumOfDigits</span><span class="p">(</span><span class="mi">3</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">sumOfDigits</span><span class="p">(</span><span class="mi">4</span><span class="p">))</span> <span class="k">print</span><span class="p">(</span><span class="n">sumOfDigits</span><span class="p">(</span><span class="mi">10000</span><span class="p">))</span></code></pre></div> <p>Output: 4 8 7 13561</p> <p>Task: Encode and decode a string in the following way: Split Words by spaces. Every plaintext character gets a two-digit numerical representation in base 16. A is 01, B is 02 and Z is 1A.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c"># Thanks to lebenf: http://stackoverflow.com/a/3226719/562769</span> <span class="n">chunks</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">l</span><span class="p">,</span> <span class="n">n</span><span class="p">:</span> <span class="p">[</span><span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">:</span> <span class="n">x</span><span class="o">+</span><span class="n">n</span><span class="p">]</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">l</span><span class="p">),</span> <span class="n">n</span><span class="p">)]</span> <span class="n">decodeWord</span><span class="o">=</span> <span class="k">lambda</span> <span class="n">s</span><span class="p">:</span> <span class="s">&quot;&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="nb">chr</span><span class="p">(</span><span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">,</span><span class="mi">16</span><span class="p">)</span><span class="o">+</span><span class="mi">64</span><span class="p">),</span><span class="n">chunks</span><span class="p">(</span><span class="n">s</span><span class="p">,</span><span class="mi">2</span><span class="p">)))</span> <span class="n">decode</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">s</span><span class="p">:</span> <span class="s">&quot; &quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="n">decodeWord</span><span class="p">,</span> <span class="n">s</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)))</span> <span class="n">encodeWord</span><span class="o">=</span> <span class="k">lambda</span> <span class="n">p</span><span class="p">:</span> <span class="s">&quot;&quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="s">&quot;</span><span class="si">%.2X</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="nb">ord</span><span class="p">(</span><span class="n">x</span><span class="p">)</span><span class="o">-</span><span class="mi">64</span><span class="p">),</span> <span class="n">p</span><span class="p">))</span> <span class="n">encode</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">p</span><span class="p">:</span> <span class="s">&quot; &quot;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="n">encodeWord</span><span class="p">,</span> <span class="n">p</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)))</span> <span class="n">cipher</span> <span class="o">=</span> <span class="n">encode</span><span class="p">(</span><span class="s">&quot;HELLO WORLD&quot;</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Cipher Text: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">cipher</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Plain Text: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">decode</span><span class="p">(</span><span class="n">cipher</span><span class="p">))</span></code></pre></div> <h2>See also</h2> <ul> <li>Wikipedia: <ul> <li><a href="http://en.wikipedia.org/wiki/Lambda_calculus">Lambda calculus</a></li> <li><a href="http://en.wikipedia.org/wiki/Filter_(higher-order_function)">filter</a></li> <li><a href="http://en.wikipedia.org/wiki/Map_(higher-order_function)">map</a></li> <li><a href="http://en.wikipedia.org/wiki/Reduce_(higher-order_function)">reduce</a></li> </ul> </li> <li><a href="http://www.python-kurs.eu/lambda.php">Python-Kurs: Lambda, filter, reduce und map</a> (German)</li> </ul> Warum kann der Mond keine Atmosphäre haben? //martin-thoma.com/warum-kann-der-mond-keine-atmosphare-haben/ Sun, 10 Jun 2012 15:22:02 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/warum-kann-der-mond-keine-atmosphare-haben <p>Ich lese gerade das Buch 2025 von Frank Schätzing, in dem es um den Abbau des Isotops <a href="http://de.wikipedia.org/wiki/Helium-3#Kernfusion"><sup>3</sup>He</a> geht. Es wird auch kurz erwähnt, dass es auf dem Mond keine Atmosphäre geben kann. Warum ist das so?</p> <h2 id="die-kurze-antwort">Die kurze Antwort</h2> <p>Der Mond ist leicht. Er übt deshalb eine weitaus geringere Anziehungskraft aus, als die Erde. Deshalb ist die Geschwindigkeit, die benötigt wird um den Mond zu verlassen auch um einiges niedriger als die Fluchtgeschwindigkeit der Erde. Gleichzeitig ist es auf dem Mond sehr heiß, die einzelnen Gas-Teilchen bewegen sich also sehr schnell. Das bedeutet, sie können den Mond verlassen.</p> <h2 id="die-lange-antwort">Die lange Antwort</h2> <h3 id="definitionen-und-groumlszligen">Definitionen und Größen</h3> <p>Die <a href="http://de.wikipedia.org/wiki/Atmosph%C3%A4re_(Astronomie)">Atmosphäre</a> bezeichnet die gasförmige Hülle um einen Himmelskörper.</p> <p>Die <a href="http://de.wikipedia.org/wiki/Fluchtgeschwindigkeit#Zweite_kosmische_Geschwindigkeit_oder_Fluchtgeschwindigkeit">Fluchtgeschwindigkeit</a></p> <p>Der Mond hat Temperaturen von bis zu 130 °C. Das sind 403,15 Kelvin. Die Masse des <a href="http://de.wikipedia.org/wiki/Mond">Mondes</a> beträgt <code>$7,349 \cdot 10^{22} kg$</code>, der Radius beträgt 1738 km. Die Atommasse von Sauerstoff beträgt <code>$15,999 u$</code>.</p> <h3 id="mittlere-geschwindigkeit-eines-gases">Mittlere Geschwindigkeit eines Gases</h3> <p>Die mittlere Geschwindigkeit eines Gases berechnet sich wie folgt: <code>$E_{Kin} = \bar E_i$</code> <code>$\Leftrightarrow \frac{1}{2} \cdot m \cdot v^2 = \frac{3}{2} \cdot k \cdot T$</code>, wobei k die <a href="http://de.wikipedia.org/wiki/Boltzmann-Konstante">Boltzmann-Konstante</a> ist und T die thermodynamische Temperatur <code>$\Leftrightarrow v^2 = \frac{3 \cdot k \cdot T}{m}$</code> Da wir die mittlere Geschwindigkeit eines Gasteilchens wollen, müssen wir die <a href="http://de.wikipedia.org/wiki/Maxwell-Boltzmann-Verteilung">Maxwell-Geschwindigkeitsverteilung</a> beachten: <code>$\Rightarrow \bar v = \sqrt{\frac{8}{2 \cdot \pi}} \sqrt{\frac{3 \cdot k \cdot T}{m}}$</code> <code>$\Leftrightarrow \sqrt{\frac{12 \cdot k \cdot T}{\pi \cdot M \cdot u}}$</code>, mit M als <a href="http://de.wikipedia.org/wiki/Atommasse">Atommasse</a> und u als <a href="http://de.wikipedia.org/wiki/Atomare_Masseneinheit">atomare Masseneinheit</a>.</p> <h3 id="berechnung-der-fluchtgeschwindigkeit">Berechnung der Fluchtgeschwindigkeit</h3> <p><code>$v_{fl} = \sqrt{\frac{2 \cdot G \cdot m}{r}}$</code>, wobei G die <a href="http://de.wikipedia.org/wiki/Gravitationskonstante">Gravitationskonstante</a>, m die Masse des Himmelskörpers und r dessen Radius. Siehe auch: <a href="http://de.wikipedia.org/wiki/Kosmische_Geschwindigkeiten">1. Kosmische Geschwindigkeit</a>.</p> <h3 id="berechnung">Berechnung</h3> <p>Nun benötigen wir noch folgende Faustregel:</p> <blockquote>Eine Faustregel besagt, dass sich in der Atmosph&auml;re eines Planeten nur solche Gase befinden, deren mittlere Geschwindigkeit kleiner als ein Sechstel der Fluchtgeschwindigkeit f&uuml;r diesen Planeten ist.</blockquote> <p>Quelle: <a href="http://www.leifiphysik.de/web_ph12/musteraufgaben/08gastheorie/atmos/atmos.htm">Leifi-Physik</a></p> <p><code>$v_{fl}(\text{Mond}) \approx \sqrt{\frac{2 \cdot (6,67384 \cdot 10^{-11} \cdot \frac{m^3}{kg \cdot s^2}) \cdot (7,349 \cdot 10^{22} kg)}{1738000 m}} \approx 2375,70 \frac{m}{s}$</code> <code>$\Rightarrow \frac{1}{6} v_{fl}(\text{Mond}) \approx 395,95$</code></p> <p>Die mittlere Geschwindigkeit von Sauerstoff bei 130 °C ist:<br /> <code>$\bar v (O_2, \text{Mond}) \approx \sqrt{\frac{12 \cdot (1,3806488 \cdot 10^{-23}) \cdot (130 + 273,15)}{\pi \cdot (2 \cdot 15,999) \cdot (1,660538921 \cdot 10^{-27})}} \cdot \frac{m}{s} \approx 632,56 \frac{m}{s}$</code><br /> Achtung: Ein Sauerstoffmolekül hat 2 Atome!</p> <p><code>$\Rightarrow \frac{1}{6} v_{fl}(\text{Mond}) &lt; \bar v (O_2, \text{Mond}) \Rightarrow$</code> Langfristig kann es keine sauerstoffhaltige Atmosphäre auf dem Mond geben.</p> Cool features of Python //martin-thoma.com/cool-features-of-python/ Fri, 08 Jun 2012 17:30:10 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cool-features-of-python <p>A friend wanted to know why I enjoy programming in Python so much more than programming in other languages. So I will describe some special features of Python which make it much easier to quickly implement algorithms.</p> <p>I also made drafts how the tasks would be solved in most programming languages. When I say most, I mean most languages that are widely spread (so C/C++/Java is much more important than almost any other languages combined). I know that those tasks would be solved completely different in functional programming languages.</p> <h2>Rapid, readable programming</h2> <h3>Intuitive looping through lists</h3> <p>You can loop through every list-like datastructure like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">for</span> <span class="n">element</span> <span class="ow">in</span> <span class="nb">list</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="n">element</span><span class="p">)</span></code></pre></div> <h3>Arbitrary Integer size</h3> <p><strong>Description</strong>: Print the sum of the digits of <code>$2^{100000}$</code>. <strong>Java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.math.BigInteger</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">BigInteger</span> <span class="n">a</span> <span class="o">=</span> <span class="k">new</span> <span class="nf">BigInteger</span><span class="o">(</span><span class="s">&quot;2&quot;</span><span class="o">);</span> <span class="n">a</span> <span class="o">=</span> <span class="n">a</span><span class="o">.</span><span class="na">pow</span><span class="o">(</span><span class="mi">100000</span><span class="o">);</span> <span class="kt">int</span> <span class="n">sum</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="o">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">a</span><span class="o">.</span><span class="na">toString</span><span class="o">().</span><span class="na">length</span><span class="o">();</span> <span class="n">i</span><span class="o">++)</span> <span class="o">{</span> <span class="n">sum</span> <span class="o">+=</span> <span class="n">a</span><span class="o">.</span><span class="na">toString</span><span class="o">().</span><span class="na">charAt</span><span class="o">(</span><span class="n">i</span><span class="o">);</span> <span class="o">}</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">sum</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>Python</strong>: (was much faster in both computation and programming time!)</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">big</span> <span class="o">=</span> <span class="mi">2</span><span class="o">**</span><span class="mi">100000</span> <span class="n">sumOfDigits</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">digit</span> <span class="ow">in</span> <span class="nb">str</span><span class="p">(</span><span class="n">big</span><span class="p">):</span> <span class="n">sumOfDigits</span> <span class="o">+=</span> <span class="nb">int</span><span class="p">(</span><span class="n">digit</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">sumOfDigits</span><span class="p">)</span></code></pre></div> <p>Python has no need for a special class as it has arbitrary length integers (see <a href="http://docs.python.org/release/3.1.5/c-api/long.html">source</a>)</p> <h3>Swich values of variables</h3> <p><strong>Description</strong>: You want to make sure, that variable a is smaller than b (<code>$a &lt; b$</code>). <strong>Most languages</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">tmp</span> <span class="o">=</span> <span class="n">a</span> <span class="n">a</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="n">b</span> <span class="o">=</span> <span class="nb">max</span><span class="p">(</span><span class="n">tmp</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">),</span> <span class="nb">max</span><span class="p">(</span><span class="n">a</span><span class="p">,</span><span class="n">b</span><span class="p">)</span></code></pre></div> <h3>Return more than one variable</h3> <p><strong>Description</strong>: Evaluate <code>$f: \mathbb{R}^2 \rightarrow \mathbb{R}^3, f(x, y) := (x^2, y^2, x+y)$</code> <strong>Most languages</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">double</span> <span class="n">function</span><span class="p">(</span><span class="n">double</span> <span class="n">x</span><span class="p">,</span> <span class="n">double</span> <span class="n">y</span><span class="p">)</span> <span class="p">{</span> <span class="n">double</span> <span class="n">returnValues</span><span class="p">[</span><span class="mi">3</span><span class="p">];</span> <span class="n">returnValues</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="n">x</span><span class="o">*</span><span class="n">x</span><span class="p">;</span> <span class="n">returnValues</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="n">y</span><span class="o">*</span><span class="n">y</span><span class="p">;</span> <span class="n">returnValues</span><span class="p">[</span><span class="mi">2</span><span class="p">]</span> <span class="o">=</span> <span class="n">x</span> <span class="o">+</span> <span class="n">y</span><span class="p">;</span> <span class="k">return</span> <span class="n">returnValues</span><span class="p">;</span> <span class="p">}</span> <span class="n">double</span> <span class="n">values</span><span class="p">[</span><span class="mi">3</span><span class="p">]</span> <span class="o">=</span> <span class="n">function</span><span class="p">(</span><span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Part 1: </span><span class="si">%.2f</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">values</span><span class="p">[</span><span class="mi">0</span><span class="p">]);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Part 3: </span><span class="si">%.2f</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">values</span><span class="p">[</span><span class="mi">2</span><span class="p">]);</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">def</span> <span class="nf">function</span> <span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span> <span class="k">return</span> <span class="p">(</span><span class="n">x</span><span class="o">*</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="o">*</span><span class="n">y</span><span class="p">,</span> <span class="n">x</span><span class="o">+</span><span class="n">y</span><span class="p">)</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span><span class="p">,</span> <span class="n">c</span> <span class="o">=</span> <span class="n">function</span><span class="p">(</span><span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Part 1: </span><span class="si">%.2f</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">a</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Part 3: </span><span class="si">%.2f</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">b</span><span class="p">)</span></code></pre></div> <p>This is called “Argument Unpacking”. In fact it does return only one variable (a tuple), but it creating the tuple is so easy that it does not feel like creating another variable.</p> <h3>Short initialisation</h3> <p><strong>Description</strong>: Get a string representation of a list from the standard library <strong>Java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kn">import</span> <span class="nn">java.util.LinkedList</span><span class="o">;</span> <span class="kn">import</span> <span class="nn">java.util.List</span><span class="o">;</span> <span class="kd">public</span> <span class="kd">class</span> <span class="nc">test</span> <span class="o">{</span> <span class="kd">public</span> <span class="kd">static</span> <span class="kt">void</span> <span class="nf">main</span><span class="o">(</span><span class="n">String</span><span class="o">[]</span> <span class="n">args</span><span class="o">)</span> <span class="o">{</span> <span class="n">List</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;</span> <span class="n">myList</span> <span class="o">=</span> <span class="k">new</span> <span class="n">LinkedList</span><span class="o">&lt;</span><span class="n">Integer</span><span class="o">&gt;();</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">1</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">3</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">3</span><span class="o">);</span> <span class="n">myList</span><span class="o">.</span><span class="na">add</span><span class="o">(</span><span class="mi">7</span><span class="o">);</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="n">myList</span><span class="o">);</span> <span class="o">}</span> <span class="o">}</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">myList</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">7</span><span class="p">]</span> <span class="k">print</span><span class="p">(</span><span class="n">myList</span><span class="p">)</span></code></pre></div> <p>Both get the same result.</p> <h3>Chaining Comparisons</h3> <p>Description: You would like to check if <code>$x \in [-5, 42]$</code>. <strong>Most languages</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="k">if</span> <span class="o">(-</span><span class="mi">5</span> <span class="o">&lt;=</span> <span class="n">x</span> <span class="o">&amp;</span><span class="n">amp</span><span class="o">;&amp;</span><span class="n">amp</span><span class="o">;</span> <span class="n">x</span> <span class="o">&lt;=</span> <span class="mi">42</span><span class="o">)</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">if</span> <span class="o">-</span><span class="mi">5</span> <span class="o">&lt;=</span> <span class="n">x</span> <span class="o">&lt;=</span> <span class="mi">42</span><span class="p">:</span></code></pre></div> <h3>Enumeration</h3> <p><strong>Description</strong>: You have a list and you would like to print it, prefixed with the index in the list. <strong>Java</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">List</span> <span class="n">myList</span> <span class="o">=</span> <span class="o">(</span><span class="n">List</span> <span class="n">initialisation</span> <span class="n">and</span> <span class="n">assignment</span><span class="o">,</span> <span class="n">multiple</span> <span class="n">lines</span><span class="o">)</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">element</span> <span class="o">:</span> <span class="n">myList</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">printf</span><span class="o">(</span><span class="s">&quot;%i: %i&quot;</span><span class="o">,</span> <span class="n">i</span><span class="o">,</span> <span class="n">element</span><span class="o">);</span> <span class="n">i</span><span class="o">++;</span> <span class="o">}</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">myList</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">7</span><span class="p">]</span> <span class="k">for</span> <span class="n">nr</span><span class="p">,</span> <span class="n">element</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">myList</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;</span><span class="si">%i</span><span class="s">: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">nr</span><span class="p">,</span> <span class="n">element</span><span class="p">))</span></code></pre></div> <h3 id="named-string-formatting">Named String formatting</h3> <p>Python allows you to give parameters names:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">print</span><span class="p">(</span><span class="s">&quot;The </span><span class="si">%(foo)s</span><span class="s"> is </span><span class="si">%(bar)i</span><span class="s">.&quot;</span> <span class="o">%</span> <span class="p">{</span><span class="s">&#39;foo&#39;</span><span class="p">:</span> <span class="s">&#39;answer&#39;</span><span class="p">,</span> <span class="s">&#39;bar&#39;</span><span class="p">:</span><span class="mi">42</span><span class="p">})</span></code></pre></div> <h3 id="any-and-all">any() and all()</h3> <p><strong>Description</strong>: You have a very long list and you want to know, if a prime is in this list. <strong>Most languages</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">List</span> <span class="n">myList</span> <span class="o">=</span> <span class="o">(</span><span class="n">List</span> <span class="n">initialisation</span> <span class="n">and</span> <span class="n">assignment</span> <span class="n">of</span> <span class="n">many</span> <span class="n">values</span><span class="o">)</span> <span class="kt">boolean</span> <span class="n">isPrimePresent</span> <span class="o">=</span> <span class="kc">false</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">element</span> <span class="o">:</span> <span class="n">myList</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">isPrime</span><span class="o">(</span><span class="n">element</span><span class="o">))</span> <span class="o">{</span> <span class="n">isPrimePresent</span> <span class="o">=</span> <span class="kc">true</span><span class="o">;</span> <span class="k">break</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span> <span class="k">if</span> <span class="o">(!</span><span class="n">isPrimePresent</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;The list did not containe a prime.&quot;</span><span class="o">);</span> <span class="o">}</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">myList</span> <span class="o">=</span> <span class="p">[</span><span class="mi">4</span><span class="p">,</span> <span class="mi">4</span><span class="p">,</span> <span class="mi">9</span><span class="p">,</span> <span class="mi">12</span><span class="p">]</span> <span class="k">if</span> <span class="ow">not</span> <span class="nb">any</span><span class="p">(</span><span class="n">isPrime</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">myList</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;The list did not contain a prime&quot;</span><span class="p">)</span></code></pre></div> <p>See also: <a href="http://stackoverflow.com/questions/10958874/exists-keyword-in-python">StackOverflow answer from steveha</a>.</p> <h2 id="testing-and-documentation">Testing and Documentation</h2> <h3 id="doctest">Doctest</h3> <p>You can write Documentation and Unit-Tests at the same time! Take a look at <a href="http://docs.python.org/library/doctest.html">doctest — Test interactive Python examples</a>.</p> <h3 id="sphinx">Sphinx</h3> <p>Documentation can be generated from partially docstrings, partially rst files with <a href="http://sphinx-doc.org/tutorial.html">Sphinx</a>. It can be uploaded to <a href="http://pythonhosted.org/">pythonhosted.org</a> just like <a href="https://pythonhosted.org/neurolab/index.html">neurolab</a> did it (see also <a href="https://pythonhosted.org/an_example_pypi_project/sphinx.html">sphinx</a>).</p> <h2 id="the-rest">The Rest</h2> <h3 id="lists-and-generators">Lists and Generators</h3> <p>I already wrote an article about <a href="../understanding-python-lists/" title="Understanding Python Lists">Python Lists</a> and <a href="../python-generators/" title="Python Generators">Python Generators</a>. I love Pythons lists ☺</p> <h3 id="for--else">for … else</h3> <p><strong>Description</strong>: You have a very long list and you want to know, if a prime is in this list. <strong>Most languages</strong>:</p> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="n">List</span> <span class="n">myList</span> <span class="o">=</span> <span class="o">(</span><span class="n">List</span> <span class="n">initialisation</span> <span class="n">and</span> <span class="n">assignment</span> <span class="n">of</span> <span class="n">many</span> <span class="n">values</span><span class="o">)</span> <span class="kt">boolean</span> <span class="n">isPrimePresent</span> <span class="o">=</span> <span class="kc">false</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="n">element</span> <span class="o">:</span> <span class="n">myList</span><span class="o">)</span> <span class="o">{</span> <span class="k">if</span> <span class="o">(</span><span class="n">isPrime</span><span class="o">(</span><span class="n">element</span><span class="o">))</span> <span class="o">{</span> <span class="n">isPrimePresent</span> <span class="o">=</span> <span class="kc">true</span><span class="o">;</span> <span class="k">break</span><span class="o">;</span> <span class="o">}</span> <span class="o">}</span> <span class="k">if</span> <span class="o">(!</span><span class="n">isPrimePresent</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;The list did not containe a prime.&quot;</span><span class="o">);</span> <span class="o">}</span></code></pre></div> <p><strong>Python</strong>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">myList</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">7</span><span class="p">]</span> <span class="k">for</span> <span class="n">element</span> <span class="ow">in</span> <span class="n">myList</span><span class="p">:</span> <span class="k">if</span> <span class="n">isPrime</span><span class="p">(</span><span class="n">element</span><span class="p">):</span> <span class="k">break</span> <span class="k">else</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;The list did not containe a prime.&quot;</span><span class="p">)</span></code></pre></div> <h3 id="step-through-lists">Step through lists</h3> <p><strong>Description</strong>: Print only every n-th element of an iterable.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="k">for</span> <span class="n">element</span> <span class="ow">in</span> <span class="n">myList</span><span class="p">[::</span><span class="n">n</span><span class="p">]:</span> <span class="k">print</span> <span class="n">elemenet</span></code></pre></div> <h3 id="dynamically-add-properties-to-objects-and-classes">Dynamically add properties to objects and classes</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">class</span> <span style="color:#B06;font-weight:bold">Node</span>(<span style="color:#369;font-weight:bold">object</span>): value = <span style="color:#00D">3</span> a = Node() b = Node() <span style="color:#080;font-weight:bold">print</span> a.value <span style="color:#D42"><span style="color:black">&quot;&quot;&quot;</span><span> colorize the node! </span><span style="color:black">&quot;&quot;&quot;</span></span> <span style="color:#777">#print a.color ==&gt; AttributeError</span> <span style="color:#777"># thats ok, although the object originally had no attribute &quot;color&quot;</span> a.color = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">white</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">print</span> a.color <span style="color:#777"># You can even add a property to the class</span> Node.special = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">here is it</span><span style="color:#710">&quot;</span></span> <span style="color:#080;font-weight:bold">print</span> b.special </pre></div> </div> </div> <h3 id="imaginary-numbers">Imaginary numbers</h3> <p>Python directly supports usage of imaginary numbers:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>(<span style="color:#f00">2j</span> + <span style="color:#00D">1</span>)**<span style="color:#00D">2</span> </pre></div> </div> </div> <p>Output: <code>(-3+4j)</code></p> <h2 id="read-also">Read also</h2> <p><a href="http://docs.python.org/tutorial/introduction.html">An Informal Introduction to Python</a></p> LaTeX-Vorlage für den Semesterbericht der Studienstiftung //martin-thoma.com/latex-vorlage-fur-den-semesterbericht-der-studienstiftung/ Mon, 04 Jun 2012 07:31:36 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/latex-vorlage-fur-den-semesterbericht-der-studienstiftung <p>Stipendiaten der Studienstiftung des deutschen Volkes müssen jedes Semester einen Studienbericht schreiben.</p> <p>Damit sich andere Stipendiaten nicht auch jedes mal die Vorlage erstellen müssen, stelle ich meine LaTeX-Vorlage hier bereit. Wenn ihr Verbesserungsvorschläge habt, könnt ihr mir gerne eine E-Mail schreiben (info@martin-thoma.de) oder einen Kommentar hinterlassen.</p> <h2>Wozu dient der Semesterbericht?</h2> <p>Im Daidalosnet steht dazu:</p> <blockquote>Der Studienbericht bietet Gelegenheit, über die wesentlichen Inhalte und Erfahrungen des letzten Semesters nachzudenken sowie die beiden Leser - den Vertrauensdozenten und den Referenten - zu informieren und an Reflexionen und Bewertungen teilnehmen zu lassen. Ohne die Berichte wäre die Studienstiftung weniger oder kaum in der Lage, ein aktuelles Wissenschaftliches Programm zu bieten und die Stipendiaten verlässlich zu beraten. Nach der Lektüre des Berichtes sollten die Leser ein Bild vom Verlauf des Studiums und von fachlichen und au&szlig;erfachlichen Aktivitäten gewonnen haben. Ein Umfang von zwei bis drei Seiten ist angemessen.</blockquote> <h2>Wer bekommt wann den Studienbericht?</h2> <blockquote>Stipendiaten, die endgültig in die Studienstiftung aufgenommen worden sind, schreiben Jahresberichte jeweils zum <strong>1. August</strong>. Stipendiaten vor der endgültigen Aufnahme schreiben Semesterberichte, jeweils zum <strong>1. März</strong> und zum 1. August.</blockquote> <p>Mit dem Semesterbericht für das WS 2012/2013 soll der Bericht nicht mehr an den zuständigen Referenten bzw. Vertrauensdozenten geschickt werden, sondern direkt ins Daidalosnet geladen werden:</p> <blockquote>Bitte laden Sie Ihren Bericht als PDF-Dokument im Daidalosnet hoch. Sie finden die Eingabemaske in Ihrem eigenen Kurzprofil ("<strong>Meine Einstellungen</strong>" unten rechts) - hier ist in der unteren Bildschirmhälfte die Rubrik "<strong>Studienberichte</strong>" zu finden. Wenn Sie hier einen als "offen" gekennzeichneten Eintrag finden, müssen Sie uns einen Bericht zukommen lassen - bitte folgen Sie dem Link in der Zeile unter "offen", um zur Eingabemaske zu gelangen. Sowohl Ihr/e Referent/in als auch Ihr/e Vertrauensdozent/in erhalten automatisch eine Kopie des Berichts per E-Mail.</blockquote> <h3>Wer ist mein zuständiger Referent bzw. mein Vertrauensdozent?</h3> <ol> <li>Logge dich im <a href="https://www.daidalosnet.de/">daidalosnet</a> ein.</li> <li>Klicke rechts unten auf "Meine Einstellungen".</li> <li>Klicke auf "Gespeicherte Daten".</li> <li>Nun sollte "Referent/in" sowie "aktueller Vertrauensdozent" dort stehen.</li> </ol> <h2>Die Vorlage</h2> <p>Hier ist die Vorlage mit Blindtext als <a href="../images/2012/06/semesterbericht-ws-2011.pdf">PDF</a>.</p> <p>Makefile:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>DOKUMENT = semesterbericht-martin-thoma-ws-2011 make: pdflatex $(DOKUMENT).tex -output-format=pdf pdflatex $(DOKUMENT).tex -output-format=pdf make clean clean: rm -rf $(TARGET) *.class *.html *.log *.aux *.out </pre></div> </div> </div> <p>LaTeX:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage[utf8]{inputenc} % this is needed for umlauts \usepackage[ngerman]{babel} % this is needed for umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage[margin=2.5cm]{geometry} %layout \usepackage{fancyhdr} % needed for the footer \usepackage{lastpage} % needed for the footer \usepackage{hyperref} % links im text \usepackage{color, colortbl} % farbige Tabellenzellen \usepackage{tabularx} \clubpenalty = 10000 % Schusterjungen verhindern \widowpenalty = 10000 % Hurenkinder verhindern %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % Hier eigene Daten einfügen % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \newcommand{\Jahr}{2011/2012} % Typ: &quot;2011 / 2012&quot; oder &quot;2012&quot; \newcommand{\Semester}{Wintersemester} % &quot;Wintersemester&quot; oder &quot;Sommersemester&quot; \newcommand{\Datum}{\today} % Wann wurde der Bericht erstellt? \newcommand{\Semesteranzahl}{1} % Das Fachsemester als Zahl \newcommand{\Gesamtsemesterzahl}{6} % Die gesamte Anzahl an Semestern \newcommand{\Abschluss}{Bachelor} \newcommand{\Studienfach}{Informatik} \newcommand{\University}{KIT} \newcommand{\Nachname}{Thoma} \newcommand{\Vorname}{Martin} \newcommand{\Strasse}{Musterstra&amp;szlig;e} \newcommand{\Hausnummer}{123} \newcommand{\PLZ}{76131} \newcommand{\Ort}{Karlsruhe} \newcommand{\Email}{info@martin-thoma.de} \newcommand{\Vertrauensdozent}{Prof. Dr. &lt;a href='../images/2012/06/semesterbericht-ws-2011.pdf'&gt;Semesterbericht WS 2011&lt;/a&gt;Mustermann} \newcommand{\Referent}{Dr. Alice Brown} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \hypersetup{ pdfauthor = {\Vorname~\Nachname}, pdfkeywords = {Studienstiftung; KIT; \Vorname~\Nachname}, pdftitle = {Semesterbericht von~\Vorname~\Nachname~-~\Semester~\Jahr} } \pagestyle{fancy} \fancyhf{} \renewcommand{\headrulewidth}{0pt} \renewcommand{\footrulewidth}{0pt} \fancyfoot[R]{Seite~\thepage~von \pageref{LastPage}} \definecolor{LightCyan}{rgb}{0.88,1,1} \pagenumbering{arabic} \begin{document} \title{Semesterbericht über das \Semester \Jahr} \author{\Vorname \Nachname} \date{\Datum} \section*{Semesterbericht über das \Semester~\Jahr} \begin{tabularx}{\textwidth}{@{}llllX} Name, Vorname: &amp; \Nachname, \Vorname &amp; Universität &amp; \University \\ Semesteradresse: &amp;\Strasse~\Hausnummer &amp; Studienfach &amp; \Studienfach \\ &amp;\PLZ~\Ort~~~~~~~ &amp; Semesterzahl &amp; \Semesteranzahl~von~\Gesamtsemesterzahl \\ &amp; &amp; Geplanter Abschluss &amp; \Abschluss \\ &amp; &amp; Vertrauensdozent &amp; \Vertrauensdozent \\ E-Mail &amp;\Email &amp; Referent &amp; \Referent \\ \end{tabularx} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % Hier bitte Text einfügen! % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \subsection*{Einleitende Zusammenfassung} \subsubsection*{1. Auf diesem Stand ist jetzt mein Studium:} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. \subsubsection*{2. Das war für mich au&amp;szlig;erhalb des Studiums von gro&amp;szlig;er Bedeutung:} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue duis dolore te feugait nulla facilisi. Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat. Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue duis dolore te feugait nulla facilisi. Nam liber tempor cum soluta nobis eleifend option congue nihil imperdiet doming id quod mazim placerat facer \subsubsection*{3. Für das nächste Semester habe ich folgende Pläne:} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. \newpage Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam: \begin{table}[h] \begin{tabular}{| l | c | c | l |} \hline \textbf{Modulbezeichnung} &amp; \textbf{SWS} &amp; \textbf{LP} &amp; \textbf{Klausur} \\ \hline \hline \rowcolor{yellow} Lineare Algebra und Analytische Geometrie &amp; 8 &amp; 9 &amp; Im SS 2012 \\ \rowcolor{yellow} Analysis I &amp; 8 &amp; 9 &amp; Im SS 2012 \\ \rowcolor{yellow} Grundbegriffe der Informatik &amp; 5 &amp; 4 &amp; Am 05. März 2012 \\ \rowcolor{yellow} Programmieren &amp; 4 &amp; 5 &amp; Abschlussaufgabe läuft \\ \rowcolor{LightCyan} Betriebssysteme und Systemarchitektur &amp; 6 &amp; 6 &amp; Am 26. März 2012 \\ \rowcolor{LightCyan} Theoretische Grundlagen der Informatik &amp; 6 &amp; 6 &amp; Benotung steht aus \\ \rowcolor{LightCyan} Wahrscheinlichkeitstheorie für Informatiker &amp; 3 &amp; 4,5 &amp; mit 1,3 bestanden \\ \hline \hline Gesamt &amp; 40 &amp; 43,5 &amp; \\ \hline \end{tabular} \begin{tabular}{| l | l | l | l |} \hline \cellcolor{yellow} &amp; Teil der Orientierungsprüfung &amp; \cellcolor{LightCyan} &amp; Pflichtmodul des 3. Semesters \\ \hline \end{tabular} \end{table} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue duis dolore te feugait nulla facilisi. Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat. Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue duis dolore te feugait nulla facilisi. Nam liber tempor cum soluta nobis eleifend option congue nihil imperdiet doming id quod mazim placerat facer.\\ \\ \Ort, der \Datum\\ \\ \Vorname~\Nachname \end{document} </pre></div> </div> </div> How many IPv6 adresses exist? //martin-thoma.com/how-many-ipv6-adresses-exist/ Fri, 01 Jun 2012 18:43:22 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-many-ipv6-adresses-exist <h2>Some general information</h2> <iframe width="512" height="288" src="http://www.youtube.com/embed/-Uwjt32NvVA" frameborder="0" allowfullscreen=""></iframe> <p>A typical IPv4 adress in a lokal network looks like this: <code>192.168.0.1</code> This is <code>11000000 10101000 00000000 00000001</code> in binary octets. You can easily see that it has 32 bits. As one bit may have two values - 0 or 1 - there are <code>$2^{32} = 4,294,967,296 \approx 4.3 \cdot 10^9$</code> possible addresses. The internet needs IP-addresses to know which information should be sent to whom. So only 4.3 billion devices can be conntected to the internet. Devices are home computers (your PCs), servers (of big companies like Google or Facebook), Smartphones. So we are currently getting out of addresses. To solve this problem, IPv6 was introduced.</p> <h2>Pure Numbers</h2> <p>IPv6 has 128 bit. This means there are the number of addresses is: <code>$2^{128} = 340282366920938463463374607431768211456 \approx 3.4 \cdot 10^{38}$</code></p> <p>Quite a lot.</p> <h2>Playing with numbers</h2> <p>Imagine the world had 10 billion people (<code>$10,000,000 = 10 \cdot 10^9 = 10^{10}$</code>). Imagine everyone bought 6 smartphones, 5 computers, 1 car, 4 tablet, 4 car radios in every year. That would be 20 internet devices for every person every year. Now you could give every device a unique address for much, much more than billion billon years! The sun is going to get a <a href="http://en.wikipedia.org/wiki/Red_giant">red giant</a> in about 4 billion years, so this is nothing we have to worry about. Calculation: <code>$\frac{2^{128}}{10^{10} \cdot 20} \approx 1.7 \cdot 10^{34}$</code></p> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Internet_Protocol">Internet Protocol</a></li> <li>UbuntuUsers: <a href="http://ikhaya.ubuntuusers.de/2012/06/01/ipv6-ueberblick/">IPv6</a> (German)</li> </ul> Vectors in C++ //martin-thoma.com/vectors-in-cpp/ Mon, 28 May 2012 12:40:52 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/vectors-in-cpp <h2>Minimal Example</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="cp">#include &lt;algorithm&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="c1">// create an empty vector</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">myVector</span><span class="p">;</span> <span class="c1">// insert one element</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">5</span><span class="p">);</span> <span class="c1">// insert another element</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">4</span><span class="p">);</span> <span class="c1">// insert more elements</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">1337</span><span class="p">);</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">42</span><span class="p">);</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">31415</span><span class="p">);</span> <span class="c1">// insert an element which was there before</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="mi">5</span><span class="p">);</span> <span class="c1">// get the third element</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;third element: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">myVector</span><span class="p">[</span><span class="mi">2</span><span class="p">]</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="c1">// removes the element at position number 6</span> <span class="n">myVector</span><span class="p">.</span><span class="n">erase</span> <span class="p">(</span><span class="n">myVector</span><span class="p">.</span><span class="n">begin</span><span class="p">()</span><span class="o">+</span><span class="mi">5</span><span class="p">);</span> <span class="c1">// removes the element with the value 4</span> <span class="n">myVector</span><span class="p">.</span><span class="n">erase</span><span class="p">(</span><span class="n">remove</span><span class="p">(</span><span class="n">myVector</span><span class="p">.</span><span class="n">begin</span><span class="p">(),</span> <span class="n">myVector</span><span class="p">.</span><span class="n">end</span><span class="p">(),</span> <span class="mi">4</span><span class="p">),</span> <span class="n">myVector</span><span class="p">.</span><span class="n">end</span><span class="p">());</span> <span class="c1">// iterate over the vector</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">myIt</span><span class="p">;</span> <span class="k">for</span><span class="p">(</span><span class="n">myIt</span><span class="o">=</span><span class="n">myVector</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">myIt</span> <span class="o">!=</span> <span class="n">myVector</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="n">myIt</span><span class="o">++</span><span class="p">){</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="o">*</span><span class="n">myIt</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; &quot;</span><span class="p">;</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">third element: 1337 <span class="m">5</span> <span class="m">1337</span> <span class="m">42</span> 31415</code></pre></div> <h2>Vector initialization</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="c1">// create a vector with 100 zeroes</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">myVector</span> <span class="p">(</span><span class="mi">100</span><span class="p">);</span></code></pre></div> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="c1">// create a vector which has 42 times the integer 100</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">myVector</span> <span class="p">(</span><span class="mi">42</span><span class="p">,</span> <span class="mi">100</span><span class="p">);</span></code></pre></div> <h2>Nested Vectors</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="c1">// create an empty vector</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">myVector</span> <span class="p">(</span><span class="mi">4</span><span class="p">);</span> <span class="c1">// add elements</span> <span class="n">myVector</span><span class="p">[</span><span class="mi">0</span><span class="p">].</span><span class="n">push_back</span><span class="p">(</span><span class="mi">1</span><span class="p">);</span> <span class="n">myVector</span><span class="p">[</span><span class="mi">0</span><span class="p">].</span><span class="n">push_back</span><span class="p">(</span><span class="mi">2</span><span class="p">);</span> <span class="n">myVector</span><span class="p">[</span><span class="mi">1</span><span class="p">].</span><span class="n">push_back</span><span class="p">(</span><span class="mi">3</span><span class="p">);</span> <span class="c1">// iterate over the vector</span> <span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">myIt</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">innerIt</span><span class="p">;</span> <span class="k">for</span><span class="p">(</span><span class="n">myIt</span><span class="o">=</span><span class="n">myVector</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">myIt</span> <span class="o">!=</span> <span class="n">myVector</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="n">myIt</span><span class="o">++</span><span class="p">){</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Inner vector: &quot;</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="n">innerIt</span><span class="o">=</span><span class="n">myIt</span><span class="o">-&gt;</span><span class="n">begin</span><span class="p">();</span><span class="n">innerIt</span><span class="o">!=</span><span class="n">myIt</span><span class="o">-&gt;</span><span class="n">end</span><span class="p">();</span><span class="n">innerIt</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="o">*</span><span class="n">innerIt</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; &quot;</span><span class="p">;</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Inner vector: <span class="m">1</span> <span class="m">2</span> Inner vector: <span class="m">3</span> Inner vector: Inner vector:</code></pre></div> <h3>Initialize nested vectors</h3> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">myInnerVector</span><span class="p">(</span><span class="mi">5</span><span class="p">,</span> <span class="mi">3</span><span class="p">);</span> <span class="n">vector</span><span class="o">&lt;</span><span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">myVector</span><span class="p">(</span><span class="mi">8</span><span class="p">,</span><span class="n">myInnerVector</span><span class="p">);</span></code></pre></div> <p>Output with the script above:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> Inner vector: <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> <span class="m">3</span> 3</code></pre></div> <p>You could also do it this way:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="n">vector</span><span class="o">&lt;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="o">&gt;</span> <span class="n">myVector</span><span class="p">(</span><span class="mi">8</span><span class="p">,</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span><span class="p">(</span><span class="mi">5</span><span class="p">,</span> <span class="mi">3</span><span class="p">));</span></code></pre></div> <h2>Some more</h2> <h3>Reverse the order</h3> <p>With reverse (<a href="http://www.cplusplus.com/reference/algorithm/reverse/">source</a>):</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;algorithm&gt;</span> <span class="cp">#include &lt;vector&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span> <span class="p">()</span> <span class="p">{</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">myvector</span><span class="p">;</span> <span class="n">vector</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;::</span><span class="n">iterator</span> <span class="n">it</span><span class="p">;</span> <span class="c1">// set some values:</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">1</span><span class="p">;</span> <span class="n">i</span><span class="o">&lt;</span><span class="mi">10</span><span class="p">;</span> <span class="o">++</span><span class="n">i</span><span class="p">)</span> <span class="n">myVector</span><span class="p">.</span><span class="n">push_back</span><span class="p">(</span><span class="n">i</span><span class="p">);</span> <span class="c1">// 1 2 3 4 5 6 7 8 9</span> <span class="n">reverse</span><span class="p">(</span><span class="n">myVector</span><span class="p">.</span><span class="n">begin</span><span class="p">(),</span><span class="n">myVector</span><span class="p">.</span><span class="n">end</span><span class="p">());</span> <span class="c1">// 9 8 7 6 5 4 3 2 1</span> <span class="c1">// print out content:</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;myVector contains:&quot;</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="n">it</span><span class="o">=</span><span class="n">myVector</span><span class="p">.</span><span class="n">begin</span><span class="p">();</span> <span class="n">it</span><span class="o">!=</span><span class="n">myVector</span><span class="p">.</span><span class="n">end</span><span class="p">();</span> <span class="o">++</span><span class="n">it</span><span class="p">)</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot; &quot;</span> <span class="o">&lt;&lt;</span> <span class="o">*</span><span class="n">it</span><span class="p">;</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>See also</h2> <ul> <li>C++ Reference: <a href="http://www.cplusplus.com/reference/stl/vector/">General information</a> and <a href="http://www.cplusplus.com/reference/stl/vector/vector/">example</a></li> <li><a href="http://stackoverflow.com/questions/3131991/iterating-over-2-dimensional-stl-vector-c">Iterating over 2-dimensional STL vector C++</a></li> </ul> Sets in C++ //martin-thoma.com/sets-in-cpp/ Mon, 28 May 2012 12:08:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sets-in-cpp <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#579">#include</span> <span style="color:#B44;font-weight:bold">&lt;iostream&gt;</span> <span style="color:#579">#include</span> <span style="color:#B44;font-weight:bold">&lt;set&gt;</span> <span style="color:#579">#include</span> <span style="color:#B44;font-weight:bold">&lt;iterator&gt;</span> <span style="color:#088;font-weight:bold">using</span> <span style="color:#080;font-weight:bold">namespace</span> std; <span style="color:#0a8;font-weight:bold">int</span> main() { <span style="color:#777">// create an empty set of integers</span> set&lt;<span style="color:#0a8;font-weight:bold">int</span>&gt; mySet; <span style="color:#777">// insert one element</span> mySet.insert(<span style="color:#00D">5</span>); <span style="color:#777">// insert another element</span> mySet.insert(<span style="color:#00D">4</span>); <span style="color:#777">// insert more elements</span> mySet.insert(<span style="color:#00D">1337</span>); mySet.insert(<span style="color:#00D">42</span>); mySet.insert(<span style="color:#00D">31415</span>); <span style="color:#777">// insert an element which was there before</span> mySet.insert(<span style="color:#00D">5</span>); <span style="color:#777">// check if 4 is in set</span> <span style="color:#0a8;font-weight:bold">bool</span> is_in = mySet.find(<span style="color:#00D">4</span>) != mySet.end(); cout &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">4 is in mySet: </span><span style="color:#710">&quot;</span></span> &lt;&lt; is_in &lt;&lt; endl; is_in = mySet.find(<span style="color:#00D">6</span>) != mySet.end(); cout &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">6 is in mySet: </span><span style="color:#710">&quot;</span></span> &lt;&lt; is_in &lt;&lt; endl; <span style="color:#777">// iterate over the set</span> set&lt;<span style="color:#0a8;font-weight:bold">int</span>&gt;::iterator myIt; <span style="color:#080;font-weight:bold">for</span>(myIt=mySet.begin(); myIt != mySet.end(); myIt++){ cout &lt;&lt; *myIt &lt;&lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>; } <span style="color:#080;font-weight:bold">return</span> <span style="color:#00D">0</span>; } </pre></div> </div> </div> <p>As find is logarithmic in <code>size()</code> (source: <a href="http://www.cplusplus.com/reference/stl/set/find/">C++ Reference</a>), the membership test is also in <code>${\cal O}(log(n))$</code>.</p> <h2>Sets of structs</h2> <p>If you want to create a set of structs, you have to create a comperator:</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="kt">bool</span> <span class="k">operator</span><span class="o">&lt;</span><span class="p">(</span><span class="k">const</span> <span class="n">Edge</span><span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="n">left</span><span class="p">,</span> <span class="k">const</span> <span class="n">Edge</span><span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="n">right</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">left</span><span class="p">.</span><span class="n">uniqueEdge</span> <span class="o">&lt;</span> <span class="n">right</span><span class="p">.</span><span class="n">uniqueEdge</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>See also</h2> <ul> <li>C++ Reference: <a href="http://www.cplusplus.com/reference/stl/set/">general information</a> and <a href="http://www.cplusplus.com/reference/stl/set/set/">example</a></li> <li><a href="http://stackoverflow.com/questions/1701067/how-to-check-that-an-element-is-in-a-stdset">How to check that an element is in a std::set?</a></li> </ul> Stacks in C++ //martin-thoma.com/stacks-in-cpp/ Mon, 28 May 2012 11:45:40 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/stacks-in-cpp <h2>Minimum Example</h2> <p>```c++ #include <iostream> #include <stack></stack></iostream></p> <p>using namespace std;</p> <p>int main(){ stack<int> myStack;</int></p> <pre><code>myStack.push(5); cout &lt;&lt; "Size of stack: " &lt;&lt; myStack.size() &lt;&lt; endl; myStack.push(4); // get the element on the top cout &lt;&lt; "Top: " &lt;&lt; myStack.top() &lt;&lt; endl; // it does NOT automatically pop! cout &lt;&lt; "Top: " &lt;&lt; myStack.top() &lt;&lt; endl; // pop has NO return value! myStack.pop(); cout &lt;&lt; "Top: " &lt;&lt; myStack.top() &lt;&lt; endl; return 0; } ``` </code></pre> <h2>Maximum number of elements</h2> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;stack&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">stack</span><span class="o">&lt;</span><span class="kt">int</span><span class="o">&gt;</span> <span class="n">s</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">i</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="mi">1000000</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">for</span> <span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">j</span><span class="o">=</span><span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="mi">100</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">s</span><span class="p">.</span><span class="n">push</span><span class="p">(</span><span class="n">i</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span> <span class="n">cout</span> <span class="o">&lt;&lt;</span> <span class="s">&quot;Size of stack: &quot;</span> <span class="o">&lt;&lt;</span> <span class="n">s</span><span class="p">.</span><span class="n">size</span><span class="p">()</span> <span class="o">&lt;&lt;</span> <span class="n">endl</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Size of stack: 100000000</code></pre></div> <p>100,000,000 could be added without any problems.</p> <h2>See also</h2> <ul> <li>C++ Reference: <a href="http://www.cplusplus.com/reference/stl/stack/">general information</a> and <a href="http://www.cplusplus.com/reference/stl/stack/stack/">example</a></li> <li><a href="http://en.wikipedia.org/wiki/Stack_(data_structure)">General information about the datastructure stack</a></li> </ul> C Puzzle #1 //martin-thoma.com/c-puzzle-1/ Mon, 21 May 2012 13:15:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/c-puzzle-1 <p>What is the output of the following programm?</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span><span class="o">*</span> <span class="nf">f</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">5</span><span class="p">;</span> <span class="k">return</span> <span class="o">&amp;</span><span class="n">i</span><span class="p">;</span> <span class="p">}</span> <span class="kt">void</span> <span class="nf">g</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">42</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">;</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span><span class="o">*</span> <span class="n">x</span> <span class="o">=</span> <span class="n">f</span><span class="p">();</span> <span class="n">g</span><span class="p">();</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;x = %d</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="o">*</span><span class="n">x</span><span class="p">);</span> <span class="n">g</span><span class="p">();</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;x = %d</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="o">*</span><span class="n">x</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h2>Short Answer</h2> <p>It depends on your compiler flags!</p> <p>If you compile it with no optimization, you might get 43:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="sb">`</span><span class="nv">$ </span>gcc -O0 cpuzzle-1.c <span class="p">;</span> ./a.out aufgabe-3.c: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>f<span class="p">&amp;</span>rsquo<span class="p">;</span>: aufgabe-3.c:5: warning: <span class="k">function</span> returns address of <span class="nb">local </span>variable <span class="nv">x</span> <span class="o">=</span> 43 <span class="nv">x</span> <span class="o">=</span> 43</code></pre></div> <p>If you compile it with 03 Optimization, you might get 5.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">$`</span> gcc -O3 cpuzzle-1.c <span class="p">;</span> ./a.out aufgabe-3.c: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>f<span class="p">&amp;</span>rsquo<span class="p">;</span>: aufgabe-3.c:5: warning: <span class="k">function</span> returns address of <span class="nb">local </span>variable <span class="nv">x</span> <span class="o">=</span> 5 <span class="nv">x</span> <span class="o">=</span> 5</code></pre></div> <h2>Long answer</h2> <h3>The general answer</h3> <p>Lets analyse this code line by line.</p> <p>Line 3 - 7 is a function <strong>f</strong> that returns a pointer to an integer. The pointer points to a local variable. As far as I know it is not defined what value should be there after you leave the function (has anybody a source for that?). The variable is a so called local or automatic variable and is located on the stack frame.</p> <p>Line 9 - 14 is a function <strong>g</strong> that doesn’t take any parameter and doesn’t return anything. This function <em>should</em> not have any influence on the behavior of the program. It puts 42 on the stack and increases it by one.</p> <p>Line 17 calls f and stores the returned function pointer in the variable x.</p> <p>Line 18 calls g. Remember that g should not have any influence on the other program. But you saved a pointer to a local variable which is not in the scope of the main function. So g is allowed to use the space which was previously used by the local variable i in the function f. It uses this space for j = 42 and increases it by 1. So if you access the address of the former variable i in f you will get 43.</p> <h3>Actual assembly code</h3> <p>You still want to get more into detail? Ok … First you should get your assembly code. If you’re running a Linux machine, you can type this into the console:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gcc -S -O0 cpuzzle-1.c <span class="p">;</span> gcc cpuzzle-1.c -o cpuzzle<span class="p">;</span> mv cpuzzle-1.s cpuzzle-1-O0.s</code></pre></div> <p>This will create a file called “cpuzzle-1.s” which contains the assembly code for the non-optimized version. Rename it into “cpuzzle-1-O0.c”. Then the same for O3:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gcc -S -O3 cpuzzle-1.c <span class="p">;</span> gcc cpuzzle-1.c -o cpuzzle<span class="p">;</span> mv cpuzzle-1.s cpuzzle-1-O3.s</code></pre></div> <p>Now you can compare those two with meld or any other diff Tool:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/05/c-puzzle-1.1-meld-300x188.png"><img src="../images/2012/05/c-puzzle-1.1-meld-300x188.png" alt="C Puzzle #1 - Assembly code part 1" width="" height="" class="size-medium wp-image-24851" /></a><p class="wp-caption-text">C Puzzle #1 - Assembly code part 1</p></div> <p>The O3 code got an additional <code>.p2align 4,,15</code></p> <blockquote>.p2align 4,,15 means: When allocating memory, align it such that each new section must start at a location with 4 0's at the end (i.e. a multiple of 16 bytes), except for if more than 15 bytes must be skipped.</blockquote> <p><span class="quote-source">Quoted from <a href="http://answers.yahoo.com/question/index?qid=20100414222831AAxKaHs">MooseBoy</a></span></p> <p>It makes sense to store the data this way, as your computer can only access blocks. If one piece of data is half in one block, half in the other, you have to make to (slow) memory-accesses.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/05/c-puzzle-1.2-meld-300x113.png"><img src="../images/2012/05/c-puzzle-1.2-meld-300x113.png" alt="C Puzzle #1 - Assembly code part 2 (the main)" width="" height="" class="size-medium wp-image-24881" /></a><p class="wp-caption-text">C Puzzle #1 - Assembly code part 2 (the main)</p></div> <p>It is quite difficult to talk about it, so I made some annotations to this code. I have to admit that I don’t know why the compiler does most of the optimizations ☹</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/05/c-puzzle-1.1-meld-annotated-300x188.png"><img src="../images/2012/05/c-puzzle-1.1-meld-annotated-300x188.png" alt="C Puzzle #1, Assembly code part 1: Annotated" width="" height="" class="size-medium wp-image-24941" /></a><p class="wp-caption-text">C Puzzle #1, Assembly code part 1: Annotated</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/05/c-puzzle-1.2-meld-annotated-300x113.png"><img src="../images/2012/05/c-puzzle-1.2-meld-annotated-300x113.png" alt="C Puzzle #1, Assembly code part 2: Annotated" width="" height="" class="size-medium wp-image-24951" /></a><p class="wp-caption-text">C Puzzle #1, Assembly code part 2: Annotated</p></div> <p>You might also be interested in <a href="http://refspecs.linuxbase.org/LSB_4.0.0/LSB-Core-generic/LSB-Core-generic/libc---printf-chk-1.html">__printf_chk</a>. An implementation is <a href="http://www.ic.unicamp.br/~islene/2s2008-mo806/libc/debug/printf_chk.c">here</a>.</p> <h2>What you should have learned</h2> <p>Never return pointers to local variables / variables in the wrong scope.</p> <h2>See also</h2> <ul> <li>Wikipedia: <ul> <li><a href="http://en.wikipedia.org/wiki/Stack_frame#Structure">Stack frame</a></li> <li><a href="http://en.wikipedia.org/wiki/Call_stack">Call Stack</a></li> <li><a href="http://en.wikipedia.org/wiki/Scope_(computer_science)">Scope</a></li> </ul> </li> <li><a href="../get-your-programs-assembly-code-and-more-information/" title="Get your programs assembly code and more information">Get your programs assembly code and more information</a></li> <li><a href="http://www.a-m-i.de/tips/stack/stack.php">Der "Stack Frame"</a> (German article about the stack frame)</li> </ul> How do Bitmasks work? //martin-thoma.com/how-do-bitmasks-work/ Fri, 18 May 2012 23:02:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-do-bitmasks-work <h2>What are Bitmasks?</h2> <p>In computer science, a <a href="http://en.wikipedia.org/wiki/Mask_(computing)">mask</a> is data that is used for bitwise operations. Essentially it is a variable.</p> <p>They are very often used in C programs.</p> <h2>Bit operators</h2> <p>These are the bit operators:</p> <ul> <li>~ Bitwise NOT (not to be confused with Logical NOT &lsquo;!&rsquo;)</li> <li>&amp; Bitwise AND (not to be confused with Logical AND &lsquo;&amp;&amp;&rsquo;)</li> <li>| Bitwise OR (again, not to be confused with Logical OR &lsquo;||&rsquo;)</li> <li>^ Bitwise XOR</li> <li>&lt;&lt; Bitwise left shift</li> <li>&gt;&gt; Bitwise right shift</li> </ul> <p>This is how the operators work:</p> <table style="border:1px solid black;" border="1"> <tr style="background-color:#ccff99"> <th>Bit A</th> <th style="border-right:1px solid #000;">Bit B</th> <th>A &amp; B</th> <th>A | B</th> <th style="border-right:1px solid #000;">A ^ B</th> <th style="border-right:1px solid #000;">~A</th> <th>A &lt;&lt; B</th> <th>A &gt;&gt; B</th> </tr> <tr style="background-color:#ffffcc;"> <td>0</td> <td style="border-right:1px solid #000;">0</td> <td>0</td> <td>0</td> <td style="border-right:1px solid #000;">0</td> <td style="border-right:1px solid #000;">1</td> <td>0</td> <td>0</td> </tr> <tr> <td>0</td> <td style="border-right:1px solid #000;">1</td> <td>0</td> <td>1</td> <td style="border-right:1px solid #000;">1</td> <td style="border-right:1px solid #000;">1</td> <td>0</td> <td>0</td> </tr> <tr style="background-color:#ffffcc;"> <td>1</td> <td style="border-right:1px solid #000;">0</td> <td>0</td> <td>1</td> <td style="border-right:1px solid #000;">1</td> <td style="border-right:1px solid #000;">0</td> <td>1</td> <td>1</td> </tr> <tr> <td>1</td> <td style="border-right:1px solid #000;">1</td> <td>1</td> <td>1</td> <td style="border-right:1px solid #000;">0</td> <td style="border-right:1px solid #000;">0</td> <td>2</td> <td>0</td> </tr> </table> <h2>Some examples</h2> <p>Lets say I have any variable named “variable” with 32 bit.</p> <p>Get the last bit:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="k">return</span> <span class="n">variable</span> <span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="mi">1</span><span class="p">;</span></code></pre></div> <p>Get the first bit:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="k">return</span> <span class="n">variable</span> <span class="o">&gt;&gt;</span> <span class="mi">31</span><span class="p">;</span></code></pre></div> <p>Get the bits 4 - 14 (11 bits):</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="k">return</span> <span class="p">(</span><span class="n">variable</span> <span class="o">&gt;&gt;</span> <span class="mi">4</span><span class="p">)</span> <span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="p">((</span><span class="mi">1</span><span class="o">&lt;&lt;</span><span class="mi">11</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span><span class="p">);</span></code></pre></div> <p>Getting the pow(2,11):</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="k">return</span> <span class="mi">1</span><span class="o">&lt;&lt;</span><span class="mi">11</span><span class="p">;</span></code></pre></div> <h2>See also</h2> <ul> <li><a href="http://stackoverflow.com/questions/231760/what-does-a-type-followed-by-t-underscore-t-represent/231807#231807">What does a type followed by _t (underscore-t) represent?</a>. Jonathan Leffler, Stackoverflow.</li> <li><a href="http://stackoverflow.com/a/9602958/562769">Why does mode_t use 4 byte?</a>. Niklas B., Stackoverflow.</li> </ul> How to visualize Graph algorithms with LaTeX //martin-thoma.com/how-to-visualize-graph-algorithms-with-latex/ Wed, 16 May 2012 13:16:29 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-visualize-graph-algorithms-with-latex <p>Tkiz is a very powerful TeX package. You can easily create visualizations of graphs and graph algorithms (if you have a template ;-) ). This post should give you a template to visualize graph algorithms with LaTeX. I recently found a great animation of Prim’s algorithm done by <a href="http://www.texample.net/tikz/examples/prims-algorithm/">Kjell Magne Fauske</a>. I’ve edited his source files to show an eulerian path. This is how it looks like:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/05/tikz-animation.gif"><img src="../images/2012/05/tikz-animation.gif" alt="LaTeX (Tikz) animation of an eulerian path" width="" height="" class="size-full wp-image-24611" /></a><p class="wp-caption-text">LaTeX (Tikz) animation of an eulerian path</p></div> <p>This animation was automatically created. See <a href="../images/2012/05/LaTeX-example.zip">Archive</a> and the intermediate <a href="../images/2012/05/tikz-animation.pdf">PDF</a>.</p> <h2>The ideas</h2> <h3>Draw the Graph</h3> <p>If you want to visualize a graph algorithm, you should first try to get the image of the graph with Tikz. First include all packages / create the general structure of the document:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[hyperref={pdfpagelabels=false}]{beamer} \usepackage{lmodern} \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage{verbatim} \usepackage{tikz} \usetikzlibrary{arrows,shapes} % see http://deic.uab.es/~iblanes/beamer_gallery/index_by_theme.html \usetheme{Frankfurt} \usefonttheme{professionalfonts} \begin{document} \begin{frame} Your content will be here. \end{frame} \end{document} </pre></div> </div> </div> <p>Simple graphs could look like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\begin{figure} \begin{tikzpicture}[-&gt;,scale=1.8, auto,swap] % Draw the vertices. \node (a) at (0,0) {$a (this is text)$}; \node (b) at (0,1) {$b$}; \node (c) at (1,1) {$c$}; \node (d) at (1,0) {$d$}; \node (e) at (3,1) {$d$}; % Connect vertices with edges and draw weights \path (a) edge node {} (b); \path (b) edge node {} (c); \path (c) edge node {} (d); \path (d) edge node {} (a); \end{tikzpicture} \end{figure} </pre></div> </div> </div> <p>You should get something similar to this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/05/simple-example-graph-300x105.png"><img src="../images/2012/05/simple-example-graph-300x105.png" alt="Simple example graph created with LaTeX and Tikz" width="" height="" class="size-medium wp-image-24691" /></a><p class="wp-caption-text">Simple example graph created with LaTeX and Tikz</p></div> <h3>Animate</h3> <p>Animations can be created with Tikz by working with layers. You don’t want to redraw the whole graph every time. Most of the time you want to overlay/underlay some parts of the graph. This can be achieved by declaring a new layer:</p> <div class="highlight"><pre><code class="language-latex" data-lang="latex"><span class="k">\pgfdeclarelayer</span><span class="nb">{</span>NAME<span class="nb">}</span></code></pre></div> <p>Then you need to tell PGF which layers are to use in the next figure:</p> <div class="highlight"><pre><code class="language-latex" data-lang="latex"><span class="k">\pgfsetlayers</span><span class="nb">{</span>LAYER LIST<span class="nb">}</span></code></pre></div> <p>The layer main should always be part of the list. Here is an example:</p> <div class="highlight"><pre><code class="language-latex" data-lang="latex"><span class="k">\pgfdeclarelayer</span><span class="nb">{</span>background<span class="nb">}</span> <span class="k">\pgfdeclarelayer</span><span class="nb">{</span>foreground<span class="nb">}</span> <span class="k">\pgfsetlayers</span><span class="nb">{</span>background,main,foreground<span class="nb">}</span></code></pre></div> <p>Now the magic begins. You consecutively add frames to the layer:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre> \begin{pgfonlayer}{background} \path&lt;2-&gt;[draw,line width=5pt,-,red!50] (a.center) edge node {} (b.center); \path&lt;10-&gt;[draw,line width=5pt,-,red!50] (b.center) edge node {} (d.center); \path&lt;12-&gt;[draw,line width=5pt,-,red!50] (d.center) edge node {} (e.center); \end{pgfonlayer} </pre></div> </div> </div> <p>The number (2, 10 and 12 in this example) indicate the frame in which it should be added. This is the absolute frame, but 1 is the first frame of the figure environment!</p> <h3>Status quo</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[hyperref={pdfpagelabels=false}]{beamer} \usepackage{lmodern} \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage{verbatim} \usepackage{tikz} \usetikzlibrary{arrows,shapes} % see http://deic.uab.es/~iblanes/beamer_gallery/index_by_theme.html \usetheme{Frankfurt} \usefonttheme{professionalfonts} \begin{document} \pgfdeclarelayer{background} \pgfdeclarelayer{foreground} \pgfsetlayers{background,main,foreground} \begin{frame} \begin{figure} \begin{tikzpicture}[-&gt;,scale=1.8, auto,swap] % Draw the vertices. \node (a) at (0,0) {$a (this is text)$}; \node (b) at (0,1) {$b$}; \node (c) at (1,1) {$c$}; \node (d) at (1,0) {$d$}; \node (e) at (3,1) {$d$}; % Connect vertices with edges and draw weights \path (a) edge node {} (b); \path (b) edge node {} (c); \path (c) edge node {} (d); \path (d) edge node {} (a); \begin{pgfonlayer}{background} \path&lt;2-&gt;[draw,line width=5pt,-,red!50] (a.center) edge node {} (b.center); \path&lt;10-&gt;[draw,line width=5pt,-,red!50] (b.center) edge node {} (d.center); \path&lt;12-&gt;[draw,line width=5pt,-,red!50] (d.center) edge node {} (e.center); \end{pgfonlayer} \end{tikzpicture} \end{figure} \end{frame} \end{document} </pre></div> </div> </div> <h3>Simplify it</h3> <p>You can make some definitions, e.g.:</p> <div class="highlight"><pre><code class="language-latex" data-lang="latex">draw,line width=5pt,-,red!50</code></pre></div> <p>can be replaced by</p> <div class="highlight"><pre><code class="language-latex" data-lang="latex"><span class="k">\tikzstyle</span><span class="nb">{</span>selected edge<span class="nb">}</span> = [draw,line width=5pt,-,red!50]</code></pre></div> <p>You can make loops:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre> % Draw the vertices. \foreach \pos / \identifier / \name in {{(0,0)/a/a (this is text)}, {(0,1)/b/b}, {(1,1)/c/c}, {(1,0)/d/d}, {(3,1)/e/d}} \node (\identifier) at \pos {$\name$}; </pre></div> </div> </div> <h2>The whole, working template</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[hyperref={pdfpagelabels=false}]{beamer} \usepackage{lmodern} \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage{verbatim} \usepackage{tikz} \usetikzlibrary{arrows,shapes} % Define some styles for graphs \tikzstyle{vertex}=[circle,fill=black!25,minimum size=20pt,inner sep=0pt] \tikzstyle{selected vertex} = [vertex, fill=red!24] \tikzstyle{blue vertex} = [vertex, fill=blue!24] \tikzstyle{edge} = [draw,thick,-] \tikzstyle{weight} = [font=\small] \tikzstyle{selected edge} = [draw,line width=5pt,-,red!50] \tikzstyle{ignored edge} = [draw,line width=5pt,-,black!20] % see http://deic.uab.es/~iblanes/beamer_gallery/index_by_theme.html \usetheme{Frankfurt} \usefonttheme{professionalfonts} % disables bottom navigation bar \beamertemplatenavigationsymbolsempty % http://tex.stackexchange.com/questions/23727/converting-beamer-slides-to-animated-images \setbeamertemplate{navigation symbols}{}% \begin{document} \pgfdeclarelayer{background} \pgfsetlayers{background,main} \begin{frame} \begin{figure} \begin{tikzpicture}[-&gt;,scale=1.8, auto,swap] % Draw the vertices. First you define a list. \foreach \pos/\name in {{(0,0)/a}, {(0,2)/b}, {(1,2)/c}, {(1,0)/d}, {(2,1)/e}, {(3,1)/f}, {(4,2)/g}, {(5,2)/h}, {(4,0)/i}, {(5,0)/j}} \node[vertex] (\name) at \pos {$\name$}; % Connect vertices with edges and draw weights \foreach \source/ \dest /\pos in {a/b/, b/c/, c/d/, d/a/, c/e/bend left, d/e/, e/c/, e/f/, f/g/, f/i/, g/f/bend right, i/f/bend left, g/h/, h/j/, j/i/, i/g/} \path (\source) edge [\pos] node {} (\dest); % Start animating the edge selection. % For convenience we use a background layer to % highlight edges. This way we don't have to worry about % the highlighting covering weight labels. \begin{pgfonlayer}{background} \foreach \source / \dest / \fr / \pos in {d/a/1/, a/b/2/, b/c/3/, c/d/4/, d/e/5/, e/c/6/, c/e/7/bend left, e/f/8/, f/g/9/, g/f/10/bend right, f/i/11/, i/g/12/, g/h/13/, h/j/14/, j/i/15/, i/f/16/bend left} \path&lt;\fr-&gt;[selected edge] (\source.center) edge [\pos] node {} (\dest.center); \end{pgfonlayer} \end{tikzpicture} \end{figure} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et. \end{frame} \end{document} </pre></div> </div> </div> <h2>Resources</h2> <ul> <li><a href="http://paws.wcu.edu/tsfoguel/tikzpgfmanual.pdf">TikZ and pgf: Manual for version 1.18</a></li> <li><a href="http://www.texample.net/tikz/examples/">TeXamples.net</a>: Great page with many Tikz-Examples</li> <li><a href="http://www.tex.ac.uk/CTAN/macros/latex/contrib/beamer/doc/beameruserguide.pdf">The beamer class</a></li> </ul> How to create UML class diagrams //martin-thoma.com/how-to-create-uml-class-diagrams/ Sun, 06 May 2012 20:38:01 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-create-uml-class-diagrams <h2>Dia</h2> <p>Creating UML diagrams with Dia works like a charm! It provides some default tools. You should simply try it. Dia is a free tool.</p> <p>Take a look at these screenshots:</p> <div style="width: 241px" class="wp-caption aligncenter"><a href="../images/2012/05/dia-create-class.png"><img src="../images/2012/05/dia-create-class.png" alt="Create a class for a class diagram in Dia" width="" height="" class="size-full wp-image-24211" /></a><p class="wp-caption-text">Create a class for a class diagram in Dia</p></div> <div style="width: 686px" class="wp-caption aligncenter"><a href="../images/2012/05/dia-class-properties.png"><img src="../images/2012/05/dia-class-properties.png" alt="Edit class properties in Dia" width="" height="" class="size-full wp-image-24221" /></a><p class="wp-caption-text">Edit class properties in Dia</p></div> <div style="width: 464px" class="wp-caption aligncenter"><a href="../images/2012/05/dia-association.png"><img src="../images/2012/05/dia-association.png" alt="Customizing associations in Dia" width="" height="" class="size-full wp-image-24231" /></a><p class="wp-caption-text">Customizing associations in Dia - adding multiplicities is so much easier in Dia than in MetaUML!</p></div> <div style="width: 529px" class="wp-caption aligncenter"><a href="../images/2012/05/Dia-ClassDiagram.png"><img src="../images/2012/05/Dia-ClassDiagram.png" alt="A quick example for a class diagram created with Dia" width="" height="" class="size-full wp-image-24251" /></a><p class="wp-caption-text">A quick example for a class diagram created with Dia</p></div> <h2>LaTeX</h2> <p>I only know MetaUML for creating class diagrams entirely in LaTeX. Does anybody know something different?</p> <p>Of course, you can include a diagram created with Dia:</p> <ol> <li>Export the diagram as PNG (antialized)</li> <li>Add something like that to your tex-file: \includegraphics[width=180mm]{myDiagramm.png}</li> </ol> <h3>MetaUML</h3> <p>A MetaUML class diagram looks like that in code (saved as myMetaDiagram.mp):</p> <div class="highlight"><pre><code class="language-text" data-lang="text">input metauml; beginfig(1); Class.World(&quot;World&quot;) (&quot;-age: int&quot;, &quot;#ressources: List&quot;) (&quot;+sayHello(): void&quot;); Class.NoHuman(&quot;Human&quot;) (&quot;-birthday: Date&quot;, &quot;-nickname: String&quot;, &quot;-secret: String&quot;) (&quot;+code(language: Language): Program&quot;); leftToRight(50)(World, NoHuman); drawObjects(World, NoHuman); link(aggregation)(NoHuman.w -- World.e); item(iAssoc)(&quot;1&quot;)(obj.n = .2[World.e,NoHuman.w]); item(iAssoc)(&quot;has &gt;&quot;)(obj.n = .5[World.e,NoHuman.w]); item(iAssoc)(&quot;0..*&quot;)(obj.n = .8[World.e,NoHuman.w]); endfig; end</code></pre></div> <p>You have to execute mpost before you can compile LaTeX. A working example is in this <a href="../images/2012/05/UML.zip">UML Archive</a>.</p> <p>It looks like that in your generated PDF file:</p> <div style="width: 686px" class="wp-caption aligncenter"><a href="../images/2012/05/MetaUML-class-diagram.png"><img src="../images/2012/05/MetaUML-class-diagram.png" alt="MetaUML class diagram" width="" height="" class="size-full wp-image-24271" /></a><p class="wp-caption-text">MetaUML class diagram</p></div> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Class_diagram">Class diagram</a>, <a href="http://en.wikipedia.org/wiki/Dia_(software)">Dia</a></li> <li>Dia: <a href="http://www.wspiegel.de/infogk12/oops/dia_einf.html#py16_2">Dia und UML</a></li> <li><a href="http://ftp.fernuni-hagen.de/ftp-dir/pub/mirrors/www.ctan.org/graphics/metapost/contrib/macros/metauml/doc/metauml_manual_0.2.5.pdf">MetaUML: Tutorial, Reference and Test Suite</a></li> <li>Freies Magazin, Mai 2012: <a href="http://www.freiesmagazin.de/freiesMagazin-2012-05">Astah &ndash; Kurzvorstellung des UML-Programms</a> (German)</li> </ul> Google Code Jam 2012 – Round 1C 2012 //martin-thoma.com/google-code-jam-2012-round-1c-2012/ Sun, 06 May 2012 14:03:54 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-2012-round-1c-2012 <p>4230 tried the first problem, but only 3189 people are listed in the <a href="http://code.google.com/codejam/contest/1781488/scoreboard?c=1781488">scoreboard</a>.</p> <ul> <li>Problem 1 (<a href="http://code.google.com/codejam/contest/1781488/dashboard#s=p0">Diamond Inheritance</a>): <ul> <li>Small Set: 3077/4230 users (73%)</li> <li>Large Set: 2387/3044 users (78%)</li> </ul> </li> <li>Problem 2 (<a href="http://code.google.com/codejam/contest/1781488/dashboard#s=p1">Out of Gas</a>): <ul> <li>Small Set: 471/766 users (61%)</li> <li>Large Set: 73/253 users (29%)</li> </ul> </li> <li>Problem 3 (<a href="http://code.google.com/codejam/contest/1781488/dashboard#s=p2">Box Factory</a>): <ul> <li>Small Set: 1071/1810 users (59%)</li> <li>Large Set: 308/788 users (39%)</li> </ul> </li> </ul> <h2>Diamond Inheritance</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">psyco</span> <span class="n">psyco</span><span class="o">.</span><span class="n">full</span><span class="p">()</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">def</span> <span class="nf">line2intlist</span><span class="p">(</span><span class="n">line</span><span class="p">):</span> <span class="nb">list</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">numbers</span> <span class="o">=</span> <span class="p">[</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span> <span class="p">]</span> <span class="k">return</span> <span class="n">numbers</span> <span class="k">def</span> <span class="nf">getAnswer</span><span class="p">(</span><span class="n">classDict</span><span class="p">,</span> <span class="n">N</span><span class="p">):</span> <span class="k">for</span> <span class="n">startPoint</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">N</span><span class="p">):</span> <span class="n">reachable</span> <span class="o">=</span> <span class="p">[</span><span class="n">startPoint</span><span class="p">]</span> <span class="n">justAppended</span> <span class="o">=</span> <span class="p">[</span><span class="n">startPoint</span><span class="p">]</span> <span class="k">while</span> <span class="nb">len</span><span class="p">(</span><span class="n">justAppended</span><span class="p">)</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">newJustAppended</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">node</span> <span class="ow">in</span> <span class="n">justAppended</span><span class="p">:</span> <span class="k">for</span> <span class="n">new</span> <span class="ow">in</span> <span class="n">classDict</span><span class="p">[</span><span class="n">node</span><span class="p">]:</span> <span class="k">if</span> <span class="n">new</span> <span class="ow">in</span> <span class="n">reachable</span><span class="p">:</span> <span class="k">return</span> <span class="s">&quot;Yes&quot;</span> <span class="k">else</span><span class="p">:</span> <span class="n">newJustAppended</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">new</span><span class="p">)</span> <span class="n">reachable</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">new</span><span class="p">)</span> <span class="n">justAppended</span> <span class="o">=</span> <span class="n">newJustAppended</span> <span class="k">return</span> <span class="s">&quot;No&quot;</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">N</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="n">classDict</span> <span class="o">=</span> <span class="p">{}</span> <span class="k">for</span> <span class="n">classNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">N</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span> <span class="n">liste</span> <span class="o">=</span> <span class="n">line2intlist</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">())</span> <span class="n">classDict</span><span class="p">[</span><span class="n">classNr</span><span class="p">]</span> <span class="o">=</span> <span class="n">liste</span><span class="p">[</span><span class="mi">1</span><span class="p">:]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">getAnswer</span><span class="p">(</span><span class="n">classDict</span><span class="p">,</span> <span class="n">N</span><span class="p">)))</span></code></pre></div> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Google_Code_Jam">Google Code Jam</a></li> <li><a href="http://www.go-hero.net/jam/12/">Google Code Jam Statistics</a></li> </ul> Google Code Jam 2012 – Round 1B 2012 //martin-thoma.com/google-code-jam-2012-round-1b-2012/ Sat, 05 May 2012 21:20:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-2012-round-1b-2012 <p>5614 tried the first problem, but only 3281 people are listed in the scoreboard. So quite a lot tried to solve a problem, but couldn’t even solve one. I think these problems were much harder than the ones from <a href="../google-code-jam-2012-round-1a-2012/" title="Google Code Jam 2012 &ndash; Round 1A 2012">Round 1A 2012</a>.</p> <ul> <li>Problem 1 (<a href="http://code.google.com/codejam/contest/1836486/dashboard#s=p0">Safety in Numbers</a>): <ul> <li>Small Set: 2695/5614 users (48%)</li> <li>Large Set: 2016/2686 users (75%)</li> </ul> </li> <li>Problem 2 (<a href="http://code.google.com/codejam/contest/1836486/dashboard#s=p1">Tide Goes In, Tide Goes Out</a>): <ul> <li>Small Set: 684/894 users (77%)</li> <li>Large Set: 620/671 users (92%)</li> </ul> </li> <li>Problem 3 (<a href="http://code.google.com/codejam/contest/1836486/dashboard#s=p2">Equal Sums</a>): <ul> <li>Small Set: 2261/2534 users (89%)</li> <li>Large Set: 149/854 users (17%)</li> </ul> </li> </ul> <h2>Safety in Numbers</h2> <p>I tried this approach: X is the sum of all points given by judges. The visitors have an equal amount of points to give. <code>$P_i$</code> is the number of total points of contestant i. <code>$J_i$</code> is the number of points of contestant i by the judges. <code>$V_i$</code> is the percentage of the visitors points contestant i gets.</p> <p>So: <code>$P_i = J_i + V_i * X$</code></p> <p>You don’t know <code>$V_i$</code> and <code>$P_i$</code>. You have to get the minimal value of <code>$V_i$</code> to guarantee that contestant <code>$i$</code> will not to be eliminated. So you have to create some kind of “worst case” for contestant i, if he gets <code>$V_i \cdot X$</code> visitor-points. The worst case is that the minimum of all remaining visitors is as high as possible. So if you think of them as players, they will always try to get a equal number of points.</p> <p>If they can get an equal number of points, you can make these (in)equations: <code>$average = (X - p_i)/(N-1)$</code> <code>$p_i + V_i \cdot X \geq avg + \frac{1-V_i}{N-1} \cdot X$</code> <code>$V_i \cdot X - \frac{1-V_i}{N-1} \cdot X \geq avg - p_i$</code> <code>$V_i X (N-1) - (1-V_i) \cdot X \geq (N-1) \cdot (avg - p_i)$</code> <code>$V_i X (N-1) - X +V_i \cdot X \geq (N-1) \cdot (avg - p_i)$</code> <code>$V_i X (N-1) +V_i \cdot X \geq (N-1) \cdot (avg - p_i) + X$</code> <code>$V_i \geq (N-1) \cdot ((avg - p_i) + X)/(X (N-1) +X)$</code> <code>$V_i \geq (N-1) \cdot ((avg - p_i) + X)/(X ((N-1) +1))$</code> <code>$V_i \geq \frac{N-1}{X \cdot N} \cdot (avg - p_i + X)$</code></p> <p>Unfortunately, its possible that the other players can’t get an equal number of points. So this approach is useless in this case.</p> <p>Here is an approach with an approximation, which also works for the large input set.</p> <div class="highlight"><pre><code class="language-cpp" data-lang="cpp"><span class="cp">#include &lt;iostream&gt;</span> <span class="cp">#include &lt;cstdio&gt;</span> <span class="k">using</span> <span class="k">namespace</span> <span class="n">std</span><span class="p">;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">testcases</span><span class="p">,</span> <span class="n">N</span><span class="p">,</span> <span class="n">sum</span><span class="p">;</span> <span class="kt">int</span> <span class="n">s</span><span class="p">[</span><span class="mi">1011</span><span class="p">];</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">testcases</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">caseNr</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="n">caseNr</span> <span class="o">&lt;=</span> <span class="n">testcases</span><span class="p">;</span> <span class="n">caseNr</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">N</span><span class="p">;</span> <span class="cm">/** the sum of all points of all contestants*/</span> <span class="n">sum</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">i</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">i</span> <span class="o">&lt;</span> <span class="n">N</span><span class="p">;</span> <span class="n">i</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="n">cin</span> <span class="o">&gt;&gt;</span> <span class="n">s</span><span class="p">[</span><span class="n">i</span><span class="p">];</span> <span class="n">sum</span> <span class="o">+=</span> <span class="n">s</span><span class="p">[</span><span class="n">i</span><span class="p">];</span> <span class="p">}</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Case #%d:&quot;</span><span class="p">,</span> <span class="n">caseNr</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">contestant</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">contestant</span> <span class="o">&lt;</span> <span class="n">N</span><span class="p">;</span> <span class="n">contestant</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// approximate the minimum for each contestant</span> <span class="kt">double</span> <span class="n">low</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">high</span> <span class="o">=</span> <span class="mi">1</span><span class="p">;</span> <span class="c1">// increase the accuracy 100 times</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">j</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">j</span> <span class="o">&lt;</span> <span class="mi">100</span><span class="p">;</span> <span class="n">j</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="kt">double</span> <span class="n">mid</span> <span class="o">=</span> <span class="p">(</span><span class="n">low</span> <span class="o">+</span> <span class="n">high</span><span class="p">)</span> <span class="o">/</span> <span class="mi">2</span><span class="p">;</span> <span class="kt">double</span> <span class="n">me</span> <span class="o">=</span> <span class="n">s</span><span class="p">[</span><span class="n">contestant</span><span class="p">]</span> <span class="o">+</span> <span class="n">mid</span> <span class="o">*</span> <span class="n">sum</span><span class="p">;</span> <span class="kt">double</span> <span class="n">remaining</span> <span class="o">=</span> <span class="mi">1</span> <span class="o">-</span> <span class="n">mid</span><span class="p">;</span> <span class="k">for</span> <span class="p">(</span><span class="kt">int</span> <span class="n">k</span> <span class="o">=</span> <span class="mi">0</span><span class="p">;</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="n">N</span> <span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span><span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="n">remaining</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">;</span> <span class="n">k</span><span class="o">++</span><span class="p">)</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="n">k</span> <span class="o">!=</span> <span class="n">contestant</span> <span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span><span class="o">&amp;</span><span class="n">amp</span><span class="p">;</span> <span class="n">s</span><span class="p">[</span><span class="n">k</span><span class="p">]</span> <span class="o">&lt;</span> <span class="n">me</span><span class="p">)</span> <span class="p">{</span> <span class="c1">// the contestant k needs at least</span> <span class="c1">// this part of all audience votes</span> <span class="n">remaining</span> <span class="o">-=</span> <span class="p">(</span><span class="n">me</span> <span class="o">-</span> <span class="n">s</span><span class="p">[</span><span class="n">k</span><span class="p">])</span> <span class="o">/</span> <span class="n">sum</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="k">if</span> <span class="p">(</span><span class="n">remaining</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">)</span> <span class="p">{</span> <span class="n">low</span> <span class="o">=</span> <span class="n">mid</span><span class="p">;</span> <span class="p">}</span> <span class="k">else</span> <span class="p">{</span> <span class="n">high</span> <span class="o">=</span> <span class="n">mid</span><span class="p">;</span> <span class="p">}</span> <span class="p">}</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot; %.6lf&quot;</span><span class="p">,</span> <span class="n">low</span> <span class="o">*</span> <span class="mi">100</span><span class="p">);</span> <span class="p">}</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="p">}</span> <span class="p">}</span></code></pre></div> <h2>Tide Goes In, Tide Goes Out</h2> <p>This one could be solved with Graphs. You calculate one Graph, where every node is one cell. Every cell / node is connected to adjacent cells. Every cell has a value which is the time when you can enter them.</p> <p>After you’ve created the graph, you can make something like that:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">graph</span> <span class="o">=</span> <span class="n">createGraph</span><span class="p">(</span><span class="n">floorHeight</span><span class="p">,</span> <span class="n">ceilingHeight</span><span class="p">)</span> <span class="n">endReached</span> <span class="o">=</span> <span class="bp">False</span> <span class="n">nodesReached</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">while</span> <span class="p">(</span><span class="ow">not</span> <span class="n">endReached</span><span class="p">):</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">getMinimumAdjacentNode</span><span class="p">(</span><span class="n">graph</span><span class="p">,</span> <span class="n">nodesReached</span><span class="p">)</span> <span class="n">nodesReached</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">tmp</span><span class="p">)</span> <span class="k">return</span> <span class="n">maxTime</span><span class="p">(</span><span class="n">nodesReached</span><span class="p">)</span></code></pre></div> <h2>Equal Sums</h2> <p>A trivial solution for the small one is to try every combination. You might want to take a look at Pythonss <a href="http://docs.python.org/library/itertools.html#itertools.combinations">itertools.combinations()</a>.</p> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Google_Code_Jam">Google Code Jam</a></li> <li><a href="http://www.go-hero.net/jam/12/">Google Code Jam Statistics</a></li> </ul> How to print Source Code with LaTeX //martin-thoma.com/how-to-print-source-code-with-latex/ Sun, 29 Apr 2012 12:04:32 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-print-source-code-with-latex <p>I often need to print source code. Some years ago for a German competition called “Bundeswettbewerb Informatik”, now for projects at my university. If you use LaTeX, you can simply include the source code into your document! Here are three examples with listings and minted. I’ve also included example PDF files.</p> <h2>listings</h2> <h3>Minimal example</h3> <div style="width: 600px" class="wp-caption aligncenter"><a href="../images/2012/04/latex-java-source-listings.png"><img src="../images/2012/04/latex-java-source-listings.png" alt="LaTeX Java Source Code: listings" width="" height="" class="size-full wp-image-23851" /></a><p class="wp-caption-text">LaTeX Java Source Code: listings</p></div> <p>Here is an minimal example how you could print Source Code with LaTeX: <a id="more"></a><a id="more-23541"></a></p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts % this is needed for correct output of umlauts in pdf \usepackage[T1]{fontenc} \usepackage[margin=2.5cm]{geometry} %layout \usepackage{listings} % needed for the inclusion of source code % this is needed for forms and links within the text \usepackage{hyperref} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % THE DOCUMENT BEGINS % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \begin{document} \lstinputlisting[language=Java]{Othello.java} \end{document} </pre></div> </div> </div> <h3>My Template</h3> <p>If you want to customize a little bit more and if you want to get highlighted (colorized) source code, you could use the following template. It looks like this as a <a href="../images/2012/04/LaTeX-Source-Code.pdf">PDF-file</a>.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage[margin=2.5cm]{geometry} %layout \usepackage{listings} % needed for the inclusion of source code % the following is needed for syntax highlighting \usepackage{color} \definecolor{dkgreen}{rgb}{0,0.6,0} \definecolor{gray}{rgb}{0.5,0.5,0.5} \definecolor{mauve}{rgb}{0.58,0,0.82} \lstset{ % language=Java, % the language of the code basicstyle=\footnotesize, % the size of the fonts that are used for the code numbers=left, % where to put the line-numbers numberstyle=\tiny\color{gray}, % the style that is used for the line-numbers stepnumber=1, % the step between two line-numbers. If it's 1, each line % will be numbered numbersep=5pt, % how far the line-numbers are from the code backgroundcolor=\color{white}, % choose the background color. You must add \usepackage{color} showspaces=false, % show spaces adding particular underscores showstringspaces=false, % underline spaces within strings showtabs=false, % show tabs within strings adding particular underscores frame=single, % adds a frame around the code rulecolor=\color{black}, % if not set, the frame-color may be changed on line-breaks within not-black text (e.g. commens (green here)) tabsize=4, % sets default tabsize to 2 spaces captionpos=b, % sets the caption-position to bottom breaklines=true, % sets automatic line breaking breakatwhitespace=false, % sets if automatic breaks should only happen at whitespace title=\lstname, % show the filename of files included with \lstinputlisting; % also try caption instead of title keywordstyle=\color{blue}, % keyword style commentstyle=\color{dkgreen}, % comment style stringstyle=\color{mauve}, % string literal style escapeinside={\%*}{*)}, % if you want to add a comment within your code morekeywords={*,...} % if you want to add more keywords to the set } % this is needed for forms and links within the text \usepackage{hyperref} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % Variablen % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \newcommand{\authorName}{Martin Thoma} \newcommand{\tags}{\authorName, my, tags} \title{This is the title} \author{\authorName} \date{\today} %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % PDF Meta information % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \hypersetup{ pdfauthor = {\authorName}, pdfkeywords = {\tags}, pdftitle = {This is the title} } %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % THE DOCUMENT BEGINS % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \begin{document} \lstinputlisting[language=Java]{Othello.java} \end{document} </pre></div> </div> </div> <h3>Supported Languages</h3> <p>The LaTeX listings package provides quite a lot of language and dialects. Each bold dialect is the default dialect:</p> <p>First the interesting ones:</p> <ul> <li>Assembler (Motorola68k, x86masm)</li> <li>bash</li> <li>C (<strong>ANSI</strong>, Handel, Objective, Sharp)</li> <li>C++ (ANSI, GNU, <strong>ISO</strong>, Visual)</li> <li>Java (empty, AspectJ)</li> <li>Python</li> <li>SQL</li> <li>TeX (AlLaTeX, common, LaTeX, <strong>plain</strong>, primitive)</li> <li>XML</li> </ul> <p>And the rest: ABAP (R/2 4.3, R/2 5.0, R/3 3.1, R/3 4.6C, <strong>R/3 6.10</strong>), ACSL, Ada (<strong>2005</strong>, 83, 95), Algol (60, <strong>68</strong>), Ant, Awk (<strong>gnu</strong>, POSIX), Basic (Visual), Caml (<strong>light</strong>, Objective), CIL, Clean, Cobol (1974, <strong>1985</strong>, ibm), Comal 80, command.com (WinXP), Comsol, csh, Delphi, Eiffel, Elan, erlang, Euphoria, Fortran (77, 90, <strong>95</strong>), GCL, Gnuplot, Haskell, HTML, IDL (empty, CORBA), inform, JVMIS, ksh, Lingo, Lisp (empty, Auto), Logo, make (empty, gnu), Mathematica (1.0, 3.0, <strong>5.2</strong>), Matlab, Mercury, MetaPost, Miranda, Mizar, ML, Modula-2, MuPAD, NASTRAN, Oberon-2, OCL (decorative, OMG), Octave, Oz, Pascal (Borland6, Standard, XSC), Perl, PHP, PL/I, Plasm, PostScript, POV, Prolog, Promela, PSTricks, R, Reduce, Rexx, RSL, Ruby, S (empty, PLUS), SAS, Scilab, sh, SHELXL, Simula (<strong>67</strong>, CII, DEC, IBM), SPARQL, tcl (empty, tk), VBScript, Verilog, VHDL (empty, AMS), VRML (97), XSLT</p> <h2>minted</h2> <p>Minted needs the package pygments:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install python-pygments </pre></div> </div> </div> <h3>Supported Languages</h3> <p>Minted supports quite a lot of languages. You can get the supported languages with this command:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:~$ pygmentize -L lexers </pre></div> </div> </div> <p>This is my output:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Pygments version 1.2.2, (c) 2006-2008 by Georg Brandl. Lexers: ~~~~~~~ * Cucumber, cucumber, Gherkin, gherkin: Gherkin (filenames *.feature) * abap: ABAP (filenames *.abap) * antlr: ANTLR [a lot more gets supported, I've shortened it] * apacheconf, aconf, apache: ApacheConf (filenames .htaccess, apache.conf, apache2.conf) * applescript: AppleScript (filenames *.applescript) * as, actionscript: ActionScript (filenames *.as) * as3, actionscript3: ActionScript 3 (filenames *.as) * aspx-cs: aspx-cs (filenames *.aspx, *.asax, *.ascx, *.ashx, *.asmx, *.axd) * aspx-vb: aspx-vb (filenames *.aspx, *.asax, *.ascx, *.ashx, *.asmx, *.axd) * asy: Asymptote (filenames *.asy) * basemake: Makefile * bash, sh: Bash (filenames *.sh, *.ebuild, *.eclass) * bat: Batchfile (filenames *.bat, *.cmd) * bbcode: BBCode * befunge: Befunge (filenames *.befunge) * boo: Boo (filenames *.boo) * brainfuck, bf: Brainfuck (filenames *.bf, *.b) * c-objdump: c-objdump (filenames *.c-objdump) * c: C (filenames *.c, *.h) * cheetah, spitfire: Cheetah (filenames *.tmpl, *.spt) * clojure, clj: Clojure (filenames *.clj) * cmake: CMake (filenames *.cmake) * common-lisp, cl: Common Lisp (filenames *.cl, *.lisp, *.el) * console: Bash Session (filenames *.sh-session) * control: Debian Control file (filenames control) * cpp, c++: C++ (filenames *.cpp, *.hpp, *.c++, *.h++, *.cc, *.hh, *.cxx, *.hxx) * cpp-objdump, c++-objdumb, cxx-objdump: cpp-objdump (filenames *.cpp-objdump, *.c++-objdump, *.cxx-objdump) * csharp, c#: C# (filenames *.cs) * css: CSS (filenames *.css) [a lot more gets supported, I've shortened it] * cython, pyx: Cython (filenames *.pyx, *.pxd, *.pxi) * d-objdump: d-objdump (filenames *.d-objdump) * d: D (filenames *.d, *.di) * delphi, pas, pascal, objectpascal: Delphi (filenames *.pas) * diff, udiff: Diff (filenames *.diff, *.patch) * django, jinja: Django/Jinja * dpatch: Darcs Patch (filenames *.dpatch, *.darcspatch) * dylan: Dylan (filenames *.dylan) * erb: ERB * erl: Erlang erl session (filenames *.erl-sh) * erlang: Erlang (filenames *.erl, *.hrl) * evoque: Evoque (filenames *.evoque) * fortran: Fortran (filenames *.f, *.f90) * gas: GAS (filenames *.s, *.S) * genshi, kid, xml+genshi, xml+kid: Genshi (filenames *.kid) * genshitext: Genshi Text * glsl: GLSL (filenames *.vert, *.frag, *.geo) * gnuplot: Gnuplot (filenames *.plot, *.plt) * go: Go (filenames *.go) * groff, nroff, man: Groff (filenames *.[1234567], *.man) * haskell, hs: Haskell (filenames *.hs) * html: HTML (filenames *.html, *.htm, *.xhtml, *.xslt) [a lot more gets supported, I've shortened it] * ini, cfg: INI (filenames *.ini, *.cfg, *.properties) * io: Io (filenames *.io) * irc: IRC logs (filenames *.weechatlog) * java: Java (filenames *.java) * js, javascript: JavaScript (filenames *.js) [a lot more gets supported, I've shortened it] * jsp: Java Server Page (filenames *.jsp) * lhs, literate-haskell: Literate Haskell (filenames *.lhs) * lighty, lighttpd: Lighttpd configuration file * llvm: LLVM (filenames *.ll) * logtalk: Logtalk (filenames *.lgt) * lua: Lua (filenames *.lua) * make, makefile, mf, bsdmake: Makefile (filenames *.mak, Makefile, makefile, Makefile.*, GNUmakefile) * mako: Mako (filenames *.mao) * mako: Mako (filenames *.mao) * matlab, octave: Matlab (filenames *.m) * matlabsession: Matlab session * minid: MiniD (filenames *.md) * modelica: Modelica (filenames *.mo) * moocode: MOOCode (filenames *.moo) * mupad: MuPAD (filenames *.mu) * mxml: MXML (filenames *.mxml) * myghty: Myghty (filenames *.myt, autodelegate) * mysql: MySQL * nasm: NASM (filenames *.asm, *.ASM) * newspeak: Newspeak (filenames *.ns2) * nginx: Nginx configuration file * numpy: NumPy * objdump: objdump (filenames *.objdump) * objective-c, objectivec, obj-c, objc: Objective-C (filenames *.m) * ocaml: OCaml (filenames *.ml, *.mli, *.mll, *.mly) * ooc: Ooc (filenames *.ooc) * perl, pl: Perl (filenames *.pl, *.pm) * php, php3, php4, php5: PHP (filenames *.php, *.php[345]) * pot, po: Gettext Catalog (filenames *.pot, *.po) * pov: POVRay (filenames *.pov, *.inc) * prolog: Prolog (filenames *.prolog, *.pro, *.pl) * py3tb: Python 3.0 Traceback (filenames *.py3tb) * pycon: Python console session * pytb: Python Traceback (filenames *.pytb) * python, py: Python (filenames *.py, *.pyw, *.sc, SConstruct, SConscript) * python3, py3: Python 3 * ragel: Ragel [a lot more gets supported, I've shortened it] * raw: Raw token data * rb, ruby: Ruby (filenames *.rb, *.rbw, Rakefile, *.rake, *.gemspec, *.rbx) * rbcon, irb: Ruby irb session * rebol: REBOL (filenames *.r, *.r3) * redcode: Redcode (filenames *.cw) * rhtml, html+erb, html+ruby: RHTML (filenames *.rhtml) * rst, rest, restructuredtext: reStructuredText (filenames *.rst, *.rest) * scala: Scala (filenames *.scala) * scheme, scm: Scheme (filenames *.scm) * smalltalk, squeak: Smalltalk (filenames *.st) * smarty: Smarty (filenames *.tpl) * sourceslist, sources.list: Debian Sourcelist (filenames sources.list) * splus, s, r: S (filenames *.S, *.R) * sql: SQL (filenames *.sql) * sqlite3: sqlite3con (filenames *.sqlite3-console) * squidconf, squid.conf, squid: SquidConf (filenames squid.conf) * tcl: Tcl (filenames *.tcl) * tcsh, csh: Tcsh (filenames *.tcsh, *.csh) * tex, latex: TeX (filenames *.tex, *.aux, *.toc) * text: Text only (filenames *.txt) * trac-wiki, moin: MoinMoin/Trac Wiki markup * vala, vapi: Vala (filenames *.vala, *.vapi) * vb.net, vbnet: VB.net (filenames *.vb, *.bas) * vim: VimL (filenames *.vim, .vimrc) [...] (a lot of XML) [...] * xml: XML (filenames *.xml, *.xsl, *.rss, *.xslt, *.xsd, *.wsdl) * xslt: XSLT (filenames *.xsl, *.xslt) * yaml: YAML (filenames *.yaml, *.yml) </pre></div> </div> </div> <h3>Example</h3> <div style="width: 623px" class="wp-caption aligncenter"><a href="../images/2012/04/latex-java-source-minted.png"><img src="../images/2012/04/latex-java-source-minted.png" alt="LaTeX Java Source Code: minted" width="" height="" class="size-full wp-image-23841" /></a><p class="wp-caption-text">LaTeX Java Source Code: minted</p></div> <p>This is the <a href="../images/2012/04/minted-source-code.pdf">PDF-file</a> produced by the following LaTeX-Code:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage[margin=2cm]{geometry} %layout \usepackage{minted} % needed for the inclusion of source code \begin{document} \renewcommand{\theFancyVerbLine}{ \sffamily\textcolor[rgb]{0.5,0.5,0.5}{\scriptsize\arabic{FancyVerbLine}}} \inputminted[linenos, numbersep=5pt, tabsize=4, frame=lines, label=Othello.java]{java}{Othello.java} \end{document} </pre></div> </div> </div> <h2>Material</h2> <p>All files can be found in <a href="../images/2012/04/LaTeX-Source-Code.zip">LaTeX-Source-Code Archive</a>.</p> <h2>See also</h2> <ul> <li>WikiBook: <a href="http://en.wikibooks.org/wiki/LaTeX/Packages/Listings">LaTeX/Packages/Listings</a></li> <li><a href="ftp://ftp.fu-berlin.de/tex/CTAN/macros/latex/contrib/listings/listings.pdf">CTAN lisings documentation</a></li> <li><a href="http://ftp.fernuni-hagen.de/ftp-dir/pub/mirrors/www.ctan.org/macros/latex/contrib/minted/minted.pdf">CTAN minted documentation</a></li> </ul> <p>You might also want to try</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>texdoc listings </pre></div> </div> </div> <p>This command will show a manual as a PDF.</p> Google Code Jam 2012 – Round 1A 2012 //martin-thoma.com/google-code-jam-2012-round-1a-2012/ Sat, 28 Apr 2012 06:11:22 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-2012-round-1a-2012 <p>3691 people are listed in the scoreboard, but 3851 tried the first problem. So I guess the number of contestants might even be higher.</p> <ul> <li>Problem 1 (<a href="http://code.google.com/codejam/contest/1645485/dashboard#s=p0">Password Problem</a>): <ul> <li>Small Set: 3511/3851 users (91%)</li> <li>Large Set: 2329/3376 users (69%)</li> </ul> </li> <li>Problem 2 (<a href="http://code.google.com/codejam/contest/1645485/dashboard#s=p1">Kingdom Rush</a>): <ul> <li>Small Set: 1912/3466 users (55%)</li> <li>Large Set: 1617/1848 users (88%)</li> </ul> </li> <li>Problem 3 (<a href="http://code.google.com/codejam/contest/1645485/dashboard#s=p2">Cruise Control</a>): <ul> <li>Small Set: 65/312 users (21%)</li> <li>Large Set: 22/42 users (52%)</li> </ul> </li> </ul> <p>Just as last time, you can execute these scripts by</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python jam.py &lt; A-small-practice.in &gt; results.txt</code></pre></div> <p><a id="more"></a><a id="more-23361"></a></p> <h2>Passwords</h2> <p>This works only for the small input set:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">line2floatlist</span><span class="p">(</span><span class="n">line</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Convert integers in one line, separated by space to a</span> <span class="sd"> list of integers.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="nb">list</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">numbers</span> <span class="o">=</span> <span class="p">[</span> <span class="nb">float</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span> <span class="p">]</span> <span class="k">return</span> <span class="n">numbers</span> <span class="k">def</span> <span class="nf">prob</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">probabilities</span><span class="p">):</span> <span class="n">typesMin</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="s">&#39;inf&#39;</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">A</span> <span class="o">+</span> <span class="mi">1</span><span class="p">):</span> <span class="n">probKorrect</span> <span class="o">=</span> <span class="mf">1.0</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="n">probabilities</span><span class="p">[</span><span class="mi">0</span><span class="p">:(</span><span class="nb">len</span><span class="p">(</span><span class="n">probabilities</span><span class="p">)</span><span class="o">-</span><span class="n">i</span><span class="p">)]:</span> <span class="n">probKorrect</span> <span class="o">*=</span> <span class="n">el</span> <span class="n">probWrong</span> <span class="o">=</span> <span class="mf">1.0</span> <span class="o">-</span> <span class="n">probKorrect</span> <span class="n">remainingTypes</span> <span class="o">=</span> <span class="n">i</span> <span class="o">+</span> <span class="p">(</span><span class="n">B</span> <span class="o">-</span> <span class="n">A</span> <span class="o">+</span> <span class="n">i</span><span class="p">)</span> <span class="o">+</span> <span class="mi">1</span> <span class="n">remainingTypesErr</span> <span class="o">=</span> <span class="n">remainingTypes</span> <span class="o">+</span> <span class="n">B</span> <span class="o">+</span> <span class="mi">1</span> <span class="n">types</span> <span class="o">=</span> <span class="n">probKorrect</span> <span class="o">*</span> <span class="n">remainingTypes</span> \ <span class="o">+</span> <span class="n">probWrong</span> <span class="o">*</span> <span class="n">remainingTypesErr</span> <span class="c">#print types</span> <span class="k">if</span> <span class="n">types</span> <span class="o">&lt;</span> <span class="n">typesMin</span><span class="p">:</span> <span class="n">typesMin</span> <span class="o">=</span> <span class="n">types</span> <span class="k">if</span> <span class="p">(</span><span class="mi">1</span><span class="o">+</span><span class="n">B</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">typesMin</span><span class="p">:</span> <span class="n">typesMin</span> <span class="o">=</span> <span class="p">(</span><span class="mi">1</span><span class="o">+</span><span class="n">B</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="k">return</span> <span class="nb">round</span><span class="p">(</span><span class="n">typesMin</span> <span class="p">,</span> <span class="mi">6</span><span class="p">)</span> <span class="c">#return typesMin</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&quot; &quot;</span><span class="p">)</span> <span class="n">A</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">B</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">probabilities</span> <span class="o">=</span> <span class="n">line2floatlist</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">())</span> <span class="c">#print ((A+1), B)</span> <span class="c">#print probabilities</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%.6lf</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">prob</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">probabilities</span><span class="p">)))</span></code></pre></div> <h2>Kingdom Rush</h2> <p>My solution works only for the small input set:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">copy</span> <span class="kn">import</span> <span class="n">deepcopy</span> <span class="k">def</span> <span class="nf">line2intlist</span><span class="p">(</span><span class="n">line</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Convert integers in one line, separated by space to a</span> <span class="sd"> list of integers.</span> <span class="sd"> &quot;&quot;&quot;</span> <span class="nb">list</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">numbers</span> <span class="o">=</span> <span class="p">[</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span> <span class="p">]</span> <span class="k">return</span> <span class="n">numbers</span> <span class="k">def</span> <span class="nf">isSolvable</span><span class="p">(</span><span class="n">starDict</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Is it possible to solve this one? &quot;&quot;&quot;</span> <span class="n">intList</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">index</span> <span class="ow">in</span> <span class="n">starDict</span><span class="p">:</span> <span class="n">wasInFor</span> <span class="o">=</span> <span class="bp">True</span> <span class="n">one</span><span class="p">,</span> <span class="n">two</span> <span class="o">=</span> <span class="n">starDict</span><span class="p">[</span><span class="n">index</span><span class="p">]</span> <span class="n">intList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">one</span><span class="p">)</span> <span class="n">intList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">two</span><span class="p">)</span> <span class="n">intList</span><span class="o">.</span><span class="n">sort</span><span class="p">()</span> <span class="k">for</span> <span class="n">levelVar</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">intList</span><span class="p">)):</span> <span class="k">if</span> <span class="n">levelVar</span> <span class="o">&lt;</span> <span class="n">intList</span><span class="p">[</span><span class="n">levelVar</span><span class="p">]:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">def</span> <span class="nf">king</span><span class="p">(</span><span class="n">starDict</span><span class="p">,</span> <span class="n">myLevel</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">myCompetes</span> <span class="o">=</span> <span class="mi">0</span><span class="p">,</span> <span class="n">partially</span> <span class="o">=</span> <span class="p">[]):</span> <span class="n">somethingChanged</span> <span class="o">=</span> <span class="bp">True</span> <span class="k">while</span> <span class="n">somethingChanged</span><span class="p">:</span> <span class="n">removeList</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">somethingChanged</span> <span class="o">=</span> <span class="bp">False</span> <span class="c">#all where i can do both</span> <span class="k">for</span> <span class="n">index</span> <span class="ow">in</span> <span class="n">starDict</span><span class="p">:</span> <span class="n">one</span><span class="p">,</span> <span class="n">two</span> <span class="o">=</span> <span class="n">starDict</span><span class="p">[</span><span class="n">index</span><span class="p">]</span> <span class="k">if</span> <span class="n">two</span> <span class="o">&lt;=</span> <span class="n">myLevel</span><span class="p">:</span> <span class="n">removeList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">index</span><span class="p">)</span> <span class="n">somethingChanged</span> <span class="o">=</span> <span class="bp">True</span> <span class="c">#remove them</span> <span class="k">for</span> <span class="n">index</span> <span class="ow">in</span> <span class="n">removeList</span><span class="p">:</span> <span class="n">myCompetes</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">del</span> <span class="n">starDict</span><span class="p">[</span><span class="n">index</span><span class="p">]</span> <span class="k">if</span> <span class="n">index</span> <span class="ow">in</span> <span class="n">partially</span><span class="p">:</span> <span class="n">myLevel</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">partially</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">index</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">myLevel</span> <span class="o">+=</span> <span class="mi">2</span> <span class="k">if</span> <span class="n">starDict</span><span class="p">:</span> <span class="n">minCompetes</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="s">&#39;inf&#39;</span><span class="p">)</span> <span class="k">for</span> <span class="n">index</span> <span class="ow">in</span> <span class="n">starDict</span><span class="p">:</span> <span class="n">one</span><span class="p">,</span> <span class="n">two</span> <span class="o">=</span> <span class="n">starDict</span><span class="p">[</span><span class="n">index</span><span class="p">]</span> <span class="k">if</span> <span class="n">one</span> <span class="o">&lt;=</span> <span class="n">myLevel</span> <span class="ow">and</span> <span class="p">(</span><span class="n">index</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">partially</span><span class="p">):</span> <span class="n">starDictTmp</span> <span class="o">=</span> <span class="n">deepcopy</span><span class="p">(</span><span class="n">starDict</span><span class="p">)</span> <span class="n">partiallyTmp</span> <span class="o">=</span> <span class="n">deepcopy</span><span class="p">(</span><span class="n">partially</span><span class="p">)</span> <span class="n">partiallyTmp</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">index</span><span class="p">)</span> <span class="n">tmpCompetes</span> <span class="o">=</span> <span class="n">king</span><span class="p">(</span><span class="n">starDictTmp</span><span class="p">,</span> <span class="n">myLevel</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">myCompetes</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">partiallyTmp</span><span class="p">)</span> <span class="k">if</span> <span class="n">tmpCompetes</span> <span class="o">&lt;</span> <span class="n">minCompetes</span><span class="p">:</span> <span class="n">minCompetes</span> <span class="o">=</span> <span class="n">tmpCompetes</span> <span class="n">myCompetes</span> <span class="o">=</span> <span class="n">minCompetes</span> <span class="k">return</span> <span class="n">myCompetes</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">levels</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="n">stars</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">levels</span><span class="p">):</span> <span class="n">stars</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">line2intlist</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">()))</span> <span class="c">#make stars dictionary</span> <span class="n">starDict</span> <span class="o">=</span> <span class="p">{}</span> <span class="n">level</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="n">stars</span><span class="p">:</span> <span class="n">starDict</span><span class="p">[</span><span class="n">level</span><span class="p">]</span> <span class="o">=</span> <span class="n">deepcopy</span><span class="p">(</span><span class="n">el</span><span class="p">)</span> <span class="n">level</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">isSolvable</span><span class="p">(</span><span class="n">starDict</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: Too Bad&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">))</span> <span class="k">else</span><span class="p">:</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">king</span><span class="p">(</span><span class="n">starDict</span><span class="p">)))</span></code></pre></div> <h2>Cruise Controll</h2> <p>Only 22 people have a perfect solution for this one.</p> <p>This is the solution of royf:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="kn">import</span> <span class="nn">itertools</span> <span class="kn">import</span> <span class="nn">math</span> <span class="kn">import</span> <span class="nn">numpy</span> <span class="k">def</span> <span class="nf">read_word</span><span class="p">(</span><span class="n">f</span><span class="p">):</span> <span class="k">return</span> <span class="nb">next</span><span class="p">(</span><span class="n">f</span><span class="p">)</span><span class="o">.</span><span class="n">strip</span><span class="p">()</span> <span class="k">def</span> <span class="nf">read_int</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">b</span><span class="o">=</span><span class="mi">10</span><span class="p">):</span> <span class="k">return</span> <span class="nb">int</span><span class="p">(</span><span class="n">read_word</span><span class="p">(</span><span class="n">f</span><span class="p">),</span> <span class="n">b</span><span class="p">)</span> <span class="k">def</span> <span class="nf">read_letters</span><span class="p">(</span><span class="n">f</span><span class="p">):</span> <span class="k">return</span> <span class="nb">list</span><span class="p">(</span><span class="n">read_word</span><span class="p">(</span><span class="n">f</span><span class="p">))</span> <span class="k">def</span> <span class="nf">read_digits</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">b</span><span class="o">=</span><span class="mi">10</span><span class="p">):</span> <span class="k">return</span> <span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">read_letters</span><span class="p">(</span><span class="n">f</span><span class="p">)]</span> <span class="k">def</span> <span class="nf">read_words</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">d</span><span class="o">=</span><span class="s">&#39; &#39;</span><span class="p">):</span> <span class="k">return</span> <span class="n">read_word</span><span class="p">(</span><span class="n">f</span><span class="p">)</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="n">d</span><span class="p">)</span> <span class="k">def</span> <span class="nf">read_ints</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">b</span><span class="o">=</span><span class="mi">10</span><span class="p">,</span> <span class="n">d</span><span class="o">=</span><span class="s">&#39; &#39;</span><span class="p">):</span> <span class="k">return</span> <span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">read_words</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">d</span><span class="p">)]</span> <span class="k">def</span> <span class="nf">read_arr</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">R</span><span class="p">,</span> <span class="n">reader</span><span class="o">=</span><span class="n">read_ints</span><span class="p">,</span> <span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span> <span class="n">res</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">R</span><span class="p">):</span> <span class="n">res</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">reader</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">))</span> <span class="k">return</span> <span class="n">res</span> <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="n">solver</span><span class="p">,</span> <span class="n">fn</span><span class="p">,</span> <span class="n">out_fn</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span> <span class="n">in_fn</span> <span class="o">=</span> <span class="n">fn</span> <span class="o">+</span> <span class="s">&#39;.in&#39;</span> <span class="k">if</span> <span class="n">out_fn</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span> <span class="n">out_fn</span> <span class="o">=</span> <span class="n">fn</span> <span class="o">+</span> <span class="s">&#39;.out&#39;</span> <span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="n">in_fn</span><span class="p">,</span> <span class="s">&#39;r&#39;</span><span class="p">)</span> <span class="k">as</span> <span class="n">fi</span><span class="p">:</span> <span class="k">with</span> <span class="nb">open</span><span class="p">(</span><span class="n">out_fn</span><span class="p">,</span> <span class="s">&#39;w&#39;</span><span class="p">)</span> <span class="k">as</span> <span class="n">fo</span><span class="p">:</span> <span class="n">T</span> <span class="o">=</span> <span class="n">read_int</span><span class="p">(</span><span class="n">fi</span><span class="p">)</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">T</span><span class="p">):</span> <span class="n">case</span> <span class="o">=</span> <span class="n">read_case</span><span class="p">(</span><span class="n">fi</span><span class="p">)</span> <span class="n">res</span> <span class="o">=</span> <span class="n">solver</span><span class="p">(</span><span class="n">case</span><span class="p">)</span> <span class="n">write_case</span><span class="p">(</span><span class="n">fo</span><span class="p">,</span> <span class="n">i</span><span class="p">,</span> <span class="n">res</span><span class="p">)</span> <span class="c">################################################################################</span> <span class="k">def</span> <span class="nf">read_case</span><span class="p">(</span><span class="n">f</span><span class="p">):</span> <span class="n">N</span> <span class="o">=</span> <span class="n">read_int</span><span class="p">(</span><span class="n">f</span><span class="p">)</span> <span class="n">Cs</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="p">(</span><span class="n">C</span><span class="p">,</span> <span class="n">S</span><span class="p">,</span> <span class="n">P</span><span class="p">)</span> <span class="o">=</span> <span class="n">read_words</span><span class="p">(</span><span class="n">f</span><span class="p">)</span> <span class="n">Cs</span><span class="o">.</span><span class="n">append</span><span class="p">((</span><span class="n">C</span><span class="p">,</span> <span class="nb">int</span><span class="p">(</span><span class="n">S</span><span class="p">),</span> <span class="nb">int</span><span class="p">(</span><span class="n">P</span><span class="p">)))</span> <span class="k">return</span> <span class="p">(</span><span class="n">N</span><span class="p">,</span> <span class="n">Cs</span><span class="p">)</span> <span class="k">def</span> <span class="nf">write_case</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">i</span><span class="p">,</span> <span class="n">res</span><span class="p">):</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;Case #</span><span class="si">%d</span><span class="s">: &#39;</span><span class="o">%</span><span class="n">i</span><span class="p">)</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;</span><span class="si">%s</span><span class="s">&#39;</span><span class="o">%</span><span class="n">res</span><span class="p">)</span> <span class="n">f</span><span class="o">.</span><span class="n">write</span><span class="p">(</span><span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span><span class="p">)</span> <span class="c">################################################################################</span> <span class="n">INF</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="s">&#39;inf&#39;</span><span class="p">)</span> <span class="kn">import</span> <span class="nn">heapq</span> <span class="k">def</span> <span class="nf">solve_small</span><span class="p">(</span><span class="n">case</span><span class="p">):</span> <span class="p">(</span><span class="n">N</span><span class="p">,</span> <span class="n">Cs</span><span class="p">)</span> <span class="o">=</span> <span class="n">case</span> <span class="n">col</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="p">(</span><span class="n">c1</span><span class="p">,</span> <span class="n">s1</span><span class="p">,</span> <span class="n">p1</span><span class="p">)</span> <span class="o">=</span> <span class="n">Cs</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">N</span><span class="p">):</span> <span class="p">(</span><span class="n">c2</span><span class="p">,</span> <span class="n">s2</span><span class="p">,</span> <span class="n">p2</span><span class="p">)</span> <span class="o">=</span> <span class="n">Cs</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="k">if</span> <span class="n">s1</span> <span class="o">==</span> <span class="n">s2</span><span class="p">:</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">p1</span><span class="o">-</span><span class="n">p2</span><span class="p">)</span> <span class="o">&lt;</span> <span class="mi">5</span><span class="p">:</span> <span class="n">heapq</span><span class="o">.</span><span class="n">heappush</span><span class="p">(</span><span class="n">col</span><span class="p">,</span> <span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="bp">True</span><span class="p">,</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">))</span> <span class="k">continue</span> <span class="n">t1</span> <span class="o">=</span> <span class="p">(</span><span class="n">p2</span><span class="o">-</span><span class="n">p1</span><span class="o">+</span><span class="mi">5</span><span class="p">)</span><span class="o">/</span><span class="p">(</span><span class="n">s1</span><span class="o">-</span><span class="n">s2</span><span class="p">)</span> <span class="n">t2</span> <span class="o">=</span> <span class="p">(</span><span class="n">p2</span><span class="o">-</span><span class="n">p1</span><span class="o">-</span><span class="mi">5</span><span class="p">)</span><span class="o">/</span><span class="p">(</span><span class="n">s1</span><span class="o">-</span><span class="n">s2</span><span class="p">)</span> <span class="k">if</span> <span class="n">t1</span> <span class="o">&gt;</span> <span class="n">t2</span><span class="p">:</span> <span class="p">(</span><span class="n">t1</span><span class="p">,</span> <span class="n">t2</span><span class="p">)</span> <span class="o">=</span> <span class="p">(</span><span class="n">t2</span><span class="p">,</span> <span class="n">t1</span><span class="p">)</span> <span class="k">if</span> <span class="n">t2</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="k">continue</span> <span class="k">if</span> <span class="n">t1</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">t1</span> <span class="o">=</span> <span class="o">-</span><span class="mi">1</span> <span class="n">heapq</span><span class="o">.</span><span class="n">heappush</span><span class="p">(</span><span class="n">col</span><span class="p">,</span> <span class="p">(</span><span class="n">t1</span><span class="p">,</span> <span class="bp">True</span><span class="p">,</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">))</span> <span class="n">heapq</span><span class="o">.</span><span class="n">heappush</span><span class="p">(</span><span class="n">col</span><span class="p">,</span> <span class="p">(</span><span class="n">t2</span><span class="p">,</span> <span class="bp">False</span><span class="p">,</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">))</span> <span class="n">l</span> <span class="o">=</span> <span class="p">[</span><span class="bp">None</span><span class="p">]</span> <span class="o">*</span> <span class="n">N</span> <span class="n">act</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="n">act</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="nb">set</span><span class="p">())</span> <span class="n">cnt</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">while</span> <span class="n">col</span><span class="p">:</span> <span class="p">(</span><span class="n">t</span><span class="p">,</span> <span class="n">c</span><span class="p">,</span> <span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">)</span> <span class="o">=</span> <span class="n">heapq</span><span class="o">.</span><span class="n">heappop</span><span class="p">(</span><span class="n">col</span><span class="p">)</span> <span class="k">if</span> <span class="n">c</span><span class="p">:</span> <span class="n">act</span><span class="p">[</span><span class="n">i</span><span class="p">]</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">j</span><span class="p">)</span> <span class="n">act</span><span class="p">[</span><span class="n">j</span><span class="p">]</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">act</span><span class="p">[</span><span class="n">i</span><span class="p">]</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">j</span><span class="p">)</span> <span class="n">act</span><span class="p">[</span><span class="n">j</span><span class="p">]</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="k">if</span> <span class="n">t</span> <span class="o">==</span> <span class="o">-</span><span class="mi">1</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">Cs</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="s">&#39;L&#39;</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="n">Cs</span><span class="p">[</span><span class="n">j</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="s">&#39;L&#39;</span> <span class="k">continue</span> <span class="k">if</span> <span class="n">c</span><span class="p">:</span> <span class="k">if</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span> <span class="k">if</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">cnt</span><span class="p">,</span> <span class="bp">True</span><span class="p">)</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">cnt</span><span class="p">,</span> <span class="bp">False</span><span class="p">)</span> <span class="n">cnt</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">True</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">False</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="bp">True</span> <span class="k">else</span><span class="p">:</span> <span class="p">(</span><span class="n">k</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="o">=</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">k</span><span class="p">,</span> <span class="ow">not</span> <span class="n">b</span><span class="p">)</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">True</span><span class="p">:</span> <span class="k">if</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="bp">False</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">True</span><span class="p">:</span> <span class="k">return</span> <span class="n">t</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">False</span><span class="p">:</span> <span class="k">pass</span> <span class="k">else</span><span class="p">:</span> <span class="p">(</span><span class="n">k</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="o">=</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">],</span> <span class="nb">tuple</span><span class="p">)</span> <span class="ow">and</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">k</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">]</span> <span class="o">=</span> <span class="n">b</span> <span class="o">!=</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">1</span><span class="p">]</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">False</span><span class="p">:</span> <span class="k">if</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="bp">True</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">True</span><span class="p">:</span> <span class="k">pass</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">False</span><span class="p">:</span> <span class="k">return</span> <span class="n">t</span> <span class="k">else</span><span class="p">:</span> <span class="p">(</span><span class="n">k</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="o">=</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">],</span> <span class="nb">tuple</span><span class="p">)</span> <span class="ow">and</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">k</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">]</span> <span class="o">=</span> <span class="n">b</span> <span class="o">==</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">1</span><span class="p">]</span> <span class="k">else</span><span class="p">:</span> <span class="p">(</span><span class="n">k</span><span class="p">,</span> <span class="n">b</span><span class="p">)</span> <span class="o">=</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="k">if</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">k</span><span class="p">,</span> <span class="ow">not</span> <span class="n">b</span><span class="p">)</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">True</span><span class="p">:</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">],</span> <span class="nb">tuple</span><span class="p">)</span> <span class="ow">and</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">k</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">]</span> <span class="o">=</span> <span class="n">b</span> <span class="o">!=</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">1</span><span class="p">]</span> <span class="k">elif</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">False</span><span class="p">:</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">],</span> <span class="nb">tuple</span><span class="p">)</span> <span class="ow">and</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">k</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">]</span> <span class="o">=</span> <span class="n">b</span> <span class="o">==</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">1</span><span class="p">]</span> <span class="k">else</span><span class="p">:</span> <span class="p">(</span><span class="n">k_</span><span class="p">,</span> <span class="n">b_</span><span class="p">)</span> <span class="o">=</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="k">if</span> <span class="n">k</span> <span class="o">==</span> <span class="n">k_</span><span class="p">:</span> <span class="k">if</span> <span class="n">b</span> <span class="o">==</span> <span class="n">b_</span><span class="p">:</span> <span class="k">return</span> <span class="n">t</span> <span class="k">else</span><span class="p">:</span> <span class="k">continue</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span> <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">],</span> <span class="nb">tuple</span><span class="p">)</span> <span class="ow">and</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">k</span><span class="p">:</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">k_</span><span class="p">,</span> <span class="ow">not</span> <span class="n">b</span> <span class="o">^</span> <span class="n">b_</span> <span class="o">^</span> <span class="n">l</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="mi">1</span><span class="p">])</span> <span class="k">else</span><span class="p">:</span> <span class="c">#end col</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">act</span><span class="p">[</span><span class="n">i</span><span class="p">]:</span> <span class="n">l</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="bp">None</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">act</span><span class="p">[</span><span class="n">j</span><span class="p">]:</span> <span class="n">l</span><span class="p">[</span><span class="n">j</span><span class="p">]</span> <span class="o">=</span> <span class="bp">None</span> <span class="k">return</span> <span class="s">&#39;Possible&#39;</span> <span class="n">solve_large</span> <span class="o">=</span> <span class="n">solve_small</span> <span class="c">##def solve_large(case):</span> <span class="n">DEBUG</span> <span class="o">=</span> <span class="s">&#39;i&#39;</span> <span class="kn">from</span> <span class="nn">run</span> <span class="kn">import</span> <span class="o">*</span></code></pre></div> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Google_Code_Jam">Google Code Jam</a></li> <li><a href="http://www.go-hero.net/jam/12/">Google Code Jam Statistics</a></li> </ul> LaTeX-Vorlage für ein Lastenheft //martin-thoma.com/latex-vorlage-fur-ein-lastenheft/ Thu, 26 Apr 2012 13:51:07 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/latex-vorlage-fur-ein-lastenheft <p>Ich habe gerade mal schnell eine Vorlage für ein Lastenheft mit LaTeX erstellt. Dieses Lastenheft beinhaltet sogar ein kleines Use-Case Beispiel, das mit MetaUML realisiert wurde. Hier ist die <a href="../images/2012/04/Lastenheft.pdf">PDF</a>, hier der <a href="../images/2012/04/Lastenheft.zip">LaTeX-Code</a>.</p> <p>Das Lastenheft könnt ihr unter Linux einfach mit dem Befehl <code>make</code> erstellen, wenn ihr in diesem Ordner seid.</p> <p>Änderungsvorschläge sind willkommen! Ich werde die hier gespeicherte Version wohl noch einige male updaten.</p> <h2>Siehe auch</h2> <ul> <li><a href="http://www.st.cs.uni-saarland.de/edu/se1/skript/notes.pdf">Softwaretechnik I</a>, S. 36</li> <li><a href="http://www2.cs.uni-paderborn.de/cs/ag-schaefer/Lehre/Lehrveranstaltungen/Praktika/Softwaretechnikpraktikum/SS06/Dokumentvorlagen/Lastenheft-Template.pdf">Beispiel der Uni Paderborn</a></li> <li><a href="http://next-internet.com/hauptstudium/texte/swt_summary.pdf">Jet Another SWT-I Resume</a>, ab S. 8</li> </ul> Eclipse für SWT I einrichten //martin-thoma.com/eclipse-fur-swt-i-einrichten/ Wed, 25 Apr 2012 22:25:11 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/eclipse-fur-swt-i-einrichten <div class="info">SWT I ist das Modul Softwaretechnik I am <a href="http://de.wikipedia.org/wiki/Karlsruher_Institut_f%C3%BCr_Technologie">KIT</a>. Dieser Blogpost richtet sich also vor allem an Studenten des KIT von Herrn <a href="http://www.ipd.uka.de/Tichy/people.php?id=15">Prof. Dr. Tichy</a>. Ich arbeite au&szlig;erdem mit Ubuntu Linux. Die momentan aktuellste Version nennt sich Oneiric Ocelot und kann bei <a href="http://wiki.ubuntuusers.de/Downloads/Oneiric_Ocelot">UbuntuUsers</a> heruntergeladen werden. Das System k&ouml;nnte z.B. in <a href="http://wiki.ubuntuusers.de/VirtualBox">VirtualBox</a> installiert werden.</div> <p><a id="more"></a><a id="more-22911"></a></p> <h2>Installation</h2> <p>Für die Installation von Java, Subversion (SVN), Eclipse und Checkstyle samt Dokumentation muss folgendes in der Konsole eingegeben werden:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install openjdk-6-jre openjdk-6-jdk openjdk-6-source openjdk-6-demo openjdk-6-doc openjdk-6-jre-headless openjdk-6-jre-lib subversion libapache2-svn eclipse checkstyle checkstyle-doc</code></pre></div> <p>Dann werden etwa 276 MB an Archiven heruntergeladen und 662 MB an zusätzlichen Packeten installiert. Bei meiner Internetverbindung (DSL 1000 ☹ ) hat das ca 40 Minuten gedauert.</p> <h2>CheckStyle</h2> <p>Siehe eclipse-cs.sourceforge.net mit <a href="http://eclipse-cs.sourceforge.net/downloads.html">detaillierten Installationsanweisungen</a>.</p> <h2>Subversive</h2> <p>Siehe eclipse.org: <a href="http://www.eclipse.org/subversive/downloads.php#indigo_stable">Download Suversive</a>. Diese Erklärung ist aber nicht so toll.</p> <p>Nach der Installation und dem Neustart von Eclipse muss man das “Subversive Connector Kit” auswählen. Kurz in der Konsole</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn --version</code></pre></div> <p>eingeben. Bei mir ist anscheinend Subversion in der Version 1.6.12 installiert. Also wähle ich “SVN Kit 1.3.7”.</p> <p>Zuerst muss man den SVN Connector installieren:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">http://community.polarion.com/projects/subversive/download/eclipse/2.0/update-site/</code></pre></div> <p>Das macht man wie mit CheckStyle.</p> <p>Dann muss man Subversive installieren:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">http://download.eclipse.org/technology/subversive/0.7/update-site/</code></pre></div> <p>Auch hier macht man es wie mit CheckStyle.</p> <p>Sobald alles klappt, sieht es etwa so aus:</p> <div style="width: 676px" class="wp-caption aligncenter"><a href="../images/2012/04/eclipse-subversive.png"><img src="../images/2012/04/eclipse-subversive.png" alt="Subversive plugin in Eclipse" width="" height="" class="size-full wp-image-23271" /></a><p class="wp-caption-text">Subversive plugin in Eclipse</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/subversive-300x290.png"><img src="../images/2012/04/subversive-300x290.png" alt="Commit mit Subversive unter Eclipse" width="" height="" class="size-medium wp-image-23751" /></a><p class="wp-caption-text">Commit mit Subversive unter Eclipse</p></div> <h2>Grundeinstellungen</h2> <p>Als erstes sollte man mal auf “Window” -&gt; “Open Perspective” -&gt; “Java” klicken.</p> <h2>Siehe auch</h2> <ul> <li><a href="http://wiki.ubuntuusers.de/Downloads">Ubuntu Downloads</a></li> <li><a href="http://wiki.ubuntuusers.de/Java/Installation/Oracle_Java">Oracle Java - Manuelle Installation unter Ubuntu</a>.</li> <li>Weitere UbuntuUsers Artikel: <a href="http://wiki.ubuntuusers.de/Eclipse">Eclipse</a>, <a href="http://wiki.ubuntuusers.de/Subversion">Subversion</a></li> <li><a href="../software-versioning-cheat-sheet/" title="Software Versioning Cheat Sheet">Software Versioning Cheat Sheet (Subversion / GIT)</a></li> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Eclipse_(IDE)">Eclipse</a>, <a href="http://de.wikipedia.org/wiki/Apache_Subversion">Subversion</a></li> <li>Wiki Books: <a href="http://de.wikibooks.org/wiki/Java_Standard:_Erste_Schritte">Java Standard: Erste Schritte</a> (habe ich NICHT gelesen! Aber f&uuml;r unsere Physiker ist das eventuell hilfreich.)</li> </ul> Wie berechnet man das charakteristische Polynom? //martin-thoma.com/wie-berechnet-man-das-charakteristische-polynom/ Sat, 21 Apr 2012 13:41:39 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-berechnet-man-das-charakteristische-polynom <p>Will man das charakteristische Polynom einer Abbildungsmatrix berechnen, so muss man zuerst sicher im Umgang mit Determinanten sein.</p> <h2>Rechenregeln f&uuml;r Determinanten</h2> <p>Man darf eine <strong>Zeile mit einer Konstanten a multiplizieren</strong>, muss dann aber die Determinante durch a teilen: <a id="more"></a><a id="more-22721"></a> <code>$ det \begin{pmatrix} 3 &amp; 2 &amp; 12 &amp; 5 \\ 2 &amp; 1 &amp; 6 &amp; 4 \\ 2 &amp; 0 &amp; 2 &amp; -3\\ 2 &amp; 2 &amp; 7 &amp; 4 \end{pmatrix} \begin{array}{c} | \cdot 2 \\ | \cdot 3 \\ | \cdot 3 \\ | \cdot 3 \end{array} = \frac{1}{2} \cdot (\frac{1}{3})^3 \cdot det \begin{pmatrix} 6 &amp; 4 &amp; 24 &amp; 10 \\ 6 &amp; 3 &amp; 18 &amp; 12 \\ 6 &amp; 0 &amp; 6 &amp; -9\\ 6 &amp; 6 &amp; 21 &amp; 12 \end{pmatrix} $</code></p> <p>Man darf zwei <strong>Zeilen / Spalten tauschen</strong>, muss dann aber die Determinante mit (-1) multiplizieren: <code>$det \begin{pmatrix} 6 &amp; 4 &amp; 24 &amp; 10 \\ 6 &amp; 3 &amp; 18 &amp; 12 \\ 6 &amp; 0 &amp; 6 &amp; -9\\ 6 &amp; 6 &amp; 21 &amp; 12 \end{pmatrix} \begin{array}{c} \cdot \\ \cdot \\ \leftarrow \\ \leftarrow \end{array} = - det \begin{pmatrix} 6 &amp; 4 &amp; 24 &amp; 10 \\ 6 &amp; 3 &amp; 18 &amp; 12 \\ 6 &amp; 6 &amp; 21 &amp; 12 \\ 6 &amp; 0 &amp; 6 &amp; -9 \end{pmatrix} = det \begin{pmatrix} 6 &amp; 24 &amp; 4 &amp; 10 \\ 6 &amp; 18 &amp; 3 &amp; 12 \\ 6 &amp; 21 &amp; 6 &amp; 12 \\ 6 &amp; 6 &amp; 0 &amp; -9 \end{pmatrix}$</code></p> <p>Man darf eine <strong>Zeile mit einer Konstanten multiplizieren und auf eine beliebige <em>andere</em> Zeile addieren</strong> (wie beim Gauss-Verfahren)</p> <p>Man darf eine <strong>Zeile und eine Spalte zugleich entfernen</strong> (Entwicklung nach Spalte / Zeile xy), muss dann aber folgendermaßen ausgleichen: Entwicklung nach der k-ten Spalte: <code>$D(a_1, ... , a_n) = \sum_{j=1}^{n}(-1)^{k+j}a_{jk}D_{jk}$</code> Entwicklung nach der i-ten Zeile: <code>$det A = \sum_{k=1}^n (-1)^{i+k}a_{ik}D_{ik}$</code> Direkt entfernen, ohne etwas weiteres zu beachten, kann man die Zeile, wenn in dieser Zeile nur eine 1 steht und diese 1 an einer ungeraden Spalte (1, …, n) ist. Eine Spalte kann man direkt entfernen, wenn in der Spalte nur an einer Stelle eine 1 steht und diese 1 an einer ungeraden Zeile (1, …, n) steht.</p> <h2>Berechnung des charakteristischen Polynoms</h2> <p>Das charakteristische Polynom einer Abbildungsmatrix A ist der Wert folgender Determinanten: <code>$det(\lambda \cdot E_n - A)$</code>, wobei <code>$E_n$</code> die Einheitsmatrix ist.</p> <h2>Beispiel</h2> <p>Siehe <a href="http://de.wikipedia.org/wiki/Charakteristisches_Polynom#Beispiel">Wikipedia</a>.</p> <h2>Berechnung am PC</h2> <p>Mit Wolfram|Alpha kann man das <a href="http://www.wolframalpha.com/widgets/view.jsp?id=27ddb8d522a2dc74e89687bd357db5a0">charakteristische Polynom</a> berechnen und auch direkt die <a href="http://www.wolframalpha.com/input/?i=Eigenvalues%7B%7B1%2C0%2C1%7D%2C%7B2%2C2%2C1%7D%2C%7B4%2C2%2C1%7D%7D">Eigenwerte</a>.</p> <h2>Wozu das Ganze?</h2> <p>An dem charakteristischem Polynom kann man direkt die Eigenwerte ablesen. Existiert eine Basis aus Eigenvektoren für den Vektorraum, dann ist eine Matrix diagonalsiierbar. Wenn eine Matrix in Diagonalform ist, dann kann man damit besonders gut rechnen.</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Determinante">Determinante</a>, <a href="http://de.wikipedia.org/wiki/Charakteristisches_Polynom">Charakteristisches Polynom</a>, <a href="http://de.wikipedia.org/wiki/Eigenwertproblem">Eigenwertproblem</a>, <a href="http://de.wikipedia.org/wiki/Diagonalmatrix">Diagonalmatrix</a></li> <li>Skript von Herrn Prof. Dr. Leuzinger, S. 131 - 142: Determinanten.</li> </ul> Software Versioning Cheat Sheet //martin-thoma.com/software-versioning-cheat-sheet/ Wed, 18 Apr 2012 07:00:59 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/software-versioning-cheat-sheet <p>This <a href="../images/2012/04/versioning-cheat-sheet.pdf">Software Versioning Cheat Sheet</a> has very basic information aboout the installation and usage of Subversion and Git. (The <a href="../images/2012/04/versioning-cheat-sheet.zip">LaTeX Source Code</a> is here.)</p> <p>If you’re at the KIT and you have SWT, then you’ll probably need this command:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn checkout https://svn.ipd.kit.edu/lehre/vorlesung/SWT1/SS12/stud/ SWT/ --username swt1</code></pre></div> <p>You will be asked for a password. I hope you remember it.</p> <h2>SVN</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn co URL LocalTarget --username yourUserName</code></pre></div> <p>Source: <a href="http://svnbook.red-bean.com/en/1.7/svn.ref.svn.c.checkout.html">svn checkout</a></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn up</code></pre></div> <p>Source: <a href="http://svnbook.red-bean.com/en/1.7/svn.ref.svn.c.update.html">svn update</a></p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn log -l 4</code></pre></div> <p>Source: <a href="http://svnbook.red-bean.com/en/1.7/svn.ref.svn.c.log.html">svn log</a></p> <h3>Updating the repository</h3> <p>You can update a SVN repository with this command:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn up <span class="o">[</span>path<span class="o">]</span></code></pre></div> <p>If you need to execute the command often, you might want to define an alias. aliases are shorthands for long commands in the bash. To create a permanent one, add the following line to your ~/.bashrc file:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">alias </span><span class="nv">swt</span><span class="o">=</span><span class="s1">&#39;svn up /home/moose/Studium/SWT&#39;</span></code></pre></div> <p>Now you only have to enter “swt” to execute “svn up /home/moose/Studium/SWT”.</p> <h3>Nice diffs</h3> <p>You can modify your config file:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>gedit ~/.subversion/config </pre></div> </div> </div> <p>and change <code>diff-cmd</code> to <code>meld</code>.</p> <h3>Compare revisions</h3> <div class="highlight"><pre><code class="language-bash" data-lang="bash">svn diff -r 63:64</code></pre></div> <p>compares revision number 63 with revision number 64 with the tool you defined (see Nice diffs).</p> <h2 id="git">Git</h2> <h3 id="global-configuration">Global configuration</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ git config --global user.name &quot;Martin Thoma&quot; $ git config --global user.email info@martin-thoma.de $ git config --global color.ui true </pre></div> </div> </div> <h3 id="nice-diffs">Nice diffs</h3> <p>If you want a GUI for <code>git diff</code>, then you should do the following:</p> <p>Install meld:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get install meld </pre></div> </div> </div> <p>Got to <code>/bin</code> and create a Shell-Script called <strong>git-meld</strong> with the following content:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>#!/bin/bash meld &quot;$2&quot; &quot;$5&quot; </pre></div> </div> </div> <p>Make it executable:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">chmod +x git-meld</code></pre></div> <p>Add it to your git configuration:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">git config --global diff.external git-meld</code></pre></div> <p>Enjoy this experience when entering <code>git diff</code>:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/git-meld-300x129.png"><img src="../images/2012/04/git-meld-300x129.png" alt="Using Meld with GIT" width="" height="" class="size-medium wp-image-35541" /></a><p class="wp-caption-text">Using Meld with GIT</p></div> <p>See also <a href="http://jeetworks.org/node/90">jeetworks.org</a> for some other solutions.</p> <h3>GitHub</h3> <h4>Preparation</h4> <p>Read the guide “<a href="https://help.github.com/articles/generating-ssh-keys">Generating SSH keys</a>” for more information on SSH and “<a href="http://git-scm.com/book/en/Getting-Started-First-Time-Git-Setup">Getting Started - First-Time Git Setup</a>” for Git-specific questions.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">cd</span> ~/.ssh ssh-keygen -t rsa -C <span class="s2">&quot;info@martin-thoma.de&quot;</span> git config --global user.name <span class="s2">&quot;Martin Thoma&quot;</span> git config --global user.email info@martin-thoma.de</code></pre></div> <h4>Clone</h4> <p>Clone a GITHub repository:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">git clone git@github.com:MartinThoma/matrix-multiplication.git</code></pre></div> <h3>Snippets</h3> <p>Reset a single file to the latest revision on the server:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">git checkout HEAD file/to/restore</code></pre></div> <p>Get the latest diff:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">git diff HEAD @<span class="o">{</span>1<span class="o">}</span></code></pre></div> <h2>Resources</h2> <ul> <li><a href="http://svnbook.red-bean.com/en/1.6/">Version Control with Subversion</a>: a great explanation how to use subversion, e.g. <a href="http://svnbook.red-bean.com/en/1.6/svn.ref.svn.c.export.html">svn export</a></li> <li>StackOverflow: <a href="http://stackoverflow.com/questions/3233059/basic-subversion-question">Which files should be put under version controll?</a></li> <li>GitHub: <a href="http://help.github.com/remotes/">Remotes</a></li> </ul> URL shortener //martin-thoma.com/url-shortener/ Mon, 16 Apr 2012 15:12:57 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/url-shortener <p>URL shortening services are Websites, which offer redirections from one of their pages with short URLs to your page (with a long URL). URL shortening services are great when you need to print URLs. I don’t like them on Websites / in e-mails as I can’t see the target, but I don’t want to type so much when I get a URL in my real live.</p> <p>These services should be used more often in my university. It’s ridiculous that all students have to note very long URLs in the first few days. It’s not a real problem, but using URL shorteners would be better.</p> <p>I’ll describe some services in the following article.<a id="more"></a><a id="more-22501"></a></p> <h2>bitly</h2> <p>Long URL: <a href="https://lists.ira.uni-karlsruhe.de/mailman/listinfo/swt1-vorlesung">https://lists.ira.uni-karlsruhe.de/mailman/listinfo/swt1-vorlesung</a> (66 characters) Short URL: <a href="http://bit.ly/HKEKD0">http://bit.ly/HKEKD0</a> (20 characters) Custom URL: <a href="http://bit.ly/SWT-List">http://bit.ly/SWT-List</a> (22 characters, but you need to sign up for free)</p> <p>Bitly does not re-use old links (<a href="https://bitly.com/pages/help#i_1_4">source</a>). You get additional information by adding a + sing at the end: <a href="http://bit.ly/HKEKD0+">http://bit.ly/HKEKD0+</a>, <a href="http://bit.ly/SWT-List+">http://bit.ly/SWT-List+</a></p> <h2>TinyURL</h2> <p>Long URL: <a href="https://lists.ira.uni-karlsruhe.de/mailman/listinfo/swt1-vorlesung">https://lists.ira.uni-karlsruhe.de/mailman/listinfo/swt1-vorlesung</a> (66 characters) Short URL: <a href="http://tinyurl.com/87oscxb">http://tinyurl.com/87oscxb</a> (26 characters) Custom URL: <a href="http://tinyurl.com/SWT-List">http://tinyurl.com/SWT-List</a> (27 characters)</p> <h2>Goo.gl</h2> <p>Long URL: <a href="https://lists.ira.uni-karlsruhe.de/mailman/listinfo/swt1-vorlesung">https://lists.ira.uni-karlsruhe.de/mailman/listinfo/swt1-vorlesung</a> (66 characters) Short URL: <a href="http://goo.gl/z5cp0">http://goo.gl/z5cp0</a> (19 characters) Custom URL: Not possible</p> <p>This service is owned by Google.</p> <p>Links do not expire and nobody can change them (<a href="http://support.google.com/websearch/bin/answer.py?hl=en&amp;answer=190768">source</a>).</p> <h2 id="quality-properties">Quality Properties</h2> <p>I think you can make a very simple list of quality properties of URL shorteners:</p> <h3 id="user-interface">User Interface</h3> <p>The user interface should be minimalistic. Goo.gl is a good example, bitly and tinyurl are still ok:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/googl.png"><img src="//martin-thoma.com/captions/googl.png" alt="Goo.gl url shortener" width="500" height="260" class="" /></a><p class="wp-caption-text">Goo.gl url shortener</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/tinyurl.png"><img src="//martin-thoma.com/captions/tinyurl.png" alt="Tinyurl url shortener" width="500" height="261" class="" /></a><p class="wp-caption-text">Tinyurl url shortener</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2015/01/bitly.png"><img src="//martin-thoma.com/captions/bitly.png" alt="Bit.ly url shortener" width="500" height="247" class="" /></a><p class="wp-caption-text">Bit.ly url shortener</p></div> <h3 id="choose-your-own-name">Choose your own name</h3> <p>If possible, the user should be able to choose the name of the short URL.</p> <h3 id="never-change-short-url">NEVER change short URL</h3> <p>Short URLs should live forever and never change.</p> <h3 id="preview">Preview</h3> <ul> <li>Adding ‘?preview’ should give you a preview of the URL</li> <li>The preview should be the default option. Only if the user actively deactivated that - which can be stored with a cookie - preview should not be shown. This is especially important in case of JavaScript in the URL / probably malicious websites</li> </ul> <h2 id="see-also">See also</h2> <ul> <li><a href="http://mashable.com/2008/01/08/url-shortening-services/">URL Toolbox: 90+ URL Shortening Services</a> - if you wish to see some more</li> <li>Wikipedia: <ul> <li><a href="http://en.wikipedia.org/wiki/Bitly">bitly</a></li> <li><a href="http://en.wikipedia.org/wiki/TinyURL">TinyURL</a></li> <li><a href="https://en.wikipedia.org/wiki/URL_shortening">URL shortening</a></li> </ul> </li> </ul> <p>Did I miss quality measures?</p> Eigenwerte, Eigenvektoren und Eigenräume //martin-thoma.com/eigenwerte-eigenvektoren-und-eigenraume/ Mon, 16 Apr 2012 08:15:32 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/eigenwerte-eigenvektoren-und-eigenraume <p><strong>Eigenwerte</strong> sind Elemente des Körpers <code>$\mathbb{K}$</code> zu einem Endomorphismus <code>$\Phi:V \rightarrow V$</code>, die folgende Eigenschaft erfüllen: <code>$\Phi(x) = \lambda x$</code> mit <code>$x \in V$</code> und <code>$x \neq 0$</code></p> <p>Alle Vektoren x sind <strong>Eigenvektoren</strong> zu diesem Eigenwert.</p> <p>Zusammen mit dem Null-Vektor bilden alle Eigenvektoren zu einem Eigenwert einer linearen Abbildung <code>$\Phi$</code> einen <strong>Eigenraum</strong>. Diesen Eigenraum bezeichnet man mit <code>$E_\lambda$</code>.</p> <h2>Interessante S&auml;tze</h2> <ul> <li>`$E_{\lambda_1} \cap E_{\lambda_2} = \emptyset$`</li> <li>Ein Endomorphismus `$\Phi$` eines n-dimensionalen `$\mathbb{K}$`-Vektorraumes hat h&ouml;chstens n Eigenwerte.</li> <li>Eine lineare Abbildung `$\Phi$` ist genau dann diagonalisierbar, wenn es eine Basis von V aus Eigenvektoren gibt.</li> <li>Wenn eine lineare Abbildung eines n-dimensionalen Vektorraums n verschiedene Eigenwerte hat, so ist sie diagonalisierbar.</li> </ul> <h2>Beispiele</h2> <h3>Etwas einfaches</h3> <p>Sei <code>$\Phi:\mathbb{R}^3 \rightarrow \mathbb{R}^3$</code> definiert durch <code>$\Phi(x) := x $</code>. Dann ist <code>$\lambda = 1$</code> der einzige Eigenwert. Der gesamte <code>$\mathbb{R}^3 \setminus \begin{pmatrix} 0 \\ 0 \\ 0 \end{pmatrix}$</code> besteht ausschließlich aus Eigenvektoren zu diesem Eigenwert. Also ist der dazugehörige Eigenraum der gesamte <code>$\mathbb{R}^3$</code>.</p> <h3>Noch immer leicht</h3> <p>Sei <code>$\Phi:\mathbb{R}^3 \rightarrow \mathbb{R}^3$</code> definiert durch <code>$\Phi(x) := ax $</code> mit <code>$a \in \mathbb{R} \setminus \{0\}$</code>. Dann ist <code>$\lambda = a$</code> der einzige Eigenwert. Der gesamte <code>$\mathbb{R}^3 \setminus \begin{pmatrix} 0 \\ 0 \\ 0 \end{pmatrix}$</code> besteht ausschließlich aus Eigenvektoren zu diesem Eigenwert. Also ist der dazugehörige Eigenraum der gesamte <code>$\mathbb{R}^3$</code>.</p> <h3>Etwas schwerer</h3> <p>Sei <code>$\Phi:\mathbb{R}^3 \rightarrow \mathbb{R}^3$</code> definiert durch <code>$\Phi(x) := \begin{pmatrix} 1 &amp; 2 &amp; 3\\ 4 &amp; 5 &amp; 6 \\ 7 &amp; 8 &amp; 9 \end{pmatrix} x $</code>.</p> <p>Die Eigenwerte sind laut <a href="http://www.wolframalpha.com/input/?i=Eigenvalues+%7B%7B1%2C2%2C3%7D%2C%7B4%2C5%2C6%7D%2C%7B7%2C8%2C9%7D%7D">Wolfram|Alpha</a>: <code>$\lambda_1 = \frac{3}{2} (5+\sqrt{33})$</code>, Eigenvektor: <code>$v_1 = \begin{pmatrix}-\frac{13}{11}+\frac{1}{22} (15+3 \sqrt{33}) \\ -\frac{1}{11}+\frac{1}{44} (15+3 \sqrt{33}) \\ 1\end{pmatrix}$</code> <code>$\lambda_2 = \frac{3}{2} (5-\sqrt{33})$</code>, Eigenvektor: <code>$v_2 = \begin{pmatrix}-\frac{13}{11}+\frac{1}{22} (15+3 \sqrt{33}) \\ -\frac{1}{11}+\frac{1}{44} (15-3 \sqrt{33}) \\ 1\end{pmatrix}$</code> <code>$\lambda_3 = 0$</code>, Eigenvektor: <code>$v_3 = \begin{pmatrix}1 \\ -2 \\ 1\end{pmatrix}$</code> - der Kern von <code>$\Phi$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=NullSpace+%7B%7B1%2C2%2C3%7D%2C%7B4%2C5%2C6%7D%2C%7B7%2C8%2C9%7D%7D">Wolfram|Alpha</a>)</p> <h2>Wozu das Ganze?</h2> <p>Mit Eigenwerten (bzw. Vektoren) kann man überprüfen, ob eine lineare Abbildung diagonalisierbar ist. Eine lineare Abbildung in Form einer Diagonalmatrix ist besonders leicht zu berechnen. Es ist also wünschenswert, die Abbildungsmatrix in Diagonalform zu bringen.</p> <p>Kennt jemand noch weitere Gründe, warum Eigenwerte / Vektoren / Räume interessant sind?</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Eigenwertproblem">Eigenwertproblem</a></li> <li>Albrecht Beutelspacher: Lineare Algebra. 7 Auflage. Vieweg+Teubner Verlag, Wiesbaden 2010, ISBN 978-3-528-66508-1, S. 202-207.</li> <li>Enrico Leuzinger: Skript zur Linearen Algebra I. S. 143-147.</li> </ul> Lernkontrolle: Lineare Algebra I //martin-thoma.com/lernkontrolle-lineare-algebra-i/ Sun, 15 Apr 2012 16:50:31 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/lernkontrolle-lineare-algebra-i <p>Hier sind ein paar <a href="../images/2012/04/lernkontrolle-lineare-algebra.pdf">Fragen zur Linearen Algebra I</a> und die <a href="../images/2012/04/lernkontrolle-lineare-algebra-loesung.pdf">Antworten</a> dazu. Die <a href="../images/2012/04/LA-lernkontrolle.zip">LaTeX-Dokumente</a> gibts natürlich auch.</p> <p>Bei ein paar Fragen, bin ich mir nicht sicher wie die Antwort lautet. Ich habs immer dazu geschrieben.</p> <p>Wenn ihr Fehler findet, hinterlasst bitte einfach hier einen Kommentar. Ich verbessere es dann. Wenn ihr gute Beispiele / Gegenbeispiele oder sogar weitere Fragen habt, könnt ihr das auch gerne in den Kommentaren schreiben.</p> <h2>Material und Quellen</h2> <p>Einige Fragen (und dazugehörige Antworten) sind so, oder so ähnlich, in folgendem Buch zu finden, das ich sehr weiterempfehlen kann:</p> <p>Albrecht Beutelspacher: Lineare Algebra, ISBN 978-3-528-66508-1.</p> Google Code Jam 2012 - Qualification Round //martin-thoma.com/google-code-jam-2012-qualification-round/ Sun, 15 Apr 2012 13:35:40 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-code-jam-2012-qualification-round <p>I’ve passed the <a href="https://code.google.com/codejam/contest/1460488/dashboard">Qualification Round</a> of Google Code Jam 2012. I’ve learned, that I am not allowed to submit the large dataset after the first 8 minutes.</p> <p>18,365 programmers took part in this contest. 15,692 had at least 20 points and advanced to the First Rounds.</p> <p>These are my solutions:</p> <h2>Problem A: Speaking in Tongues</h2> <p>This one was easy. It’s a <a href="http://en.wikipedia.org/wiki/Simple_substitution#Simple_substitution">simple substitution cipher</a>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">decode</span><span class="p">(</span><span class="n">ciphertext</span><span class="p">,</span> <span class="n">key</span><span class="o">=</span><span class="s">&quot;ynficwlbkuomxsevzpdrjgthaq&quot;</span><span class="p">,</span> <span class="n">alphabet</span><span class="o">=</span><span class="s">&quot;abcdefghijklmnopqrstuvwxyz&quot;</span><span class="p">):</span> <span class="n">dic</span><span class="o">=</span><span class="p">{}</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span><span class="nb">len</span><span class="p">(</span><span class="n">key</span><span class="p">)):</span> <span class="n">dic</span><span class="p">[</span><span class="n">key</span><span class="p">[</span><span class="n">i</span><span class="p">]]</span> <span class="o">=</span> <span class="n">alphabet</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="n">plaintext</span><span class="o">=</span><span class="s">&quot;&quot;</span> <span class="k">for</span> <span class="n">l</span> <span class="ow">in</span> <span class="n">ciphertext</span><span class="p">:</span> <span class="k">if</span> <span class="n">l</span> <span class="ow">in</span> <span class="n">dic</span><span class="p">:</span> <span class="n">l</span><span class="o">=</span><span class="n">dic</span><span class="p">[</span><span class="n">l</span><span class="p">]</span> <span class="n">plaintext</span><span class="o">+=</span><span class="n">l</span> <span class="k">return</span> <span class="n">plaintext</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">cipher</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">decode</span><span class="p">(</span><span class="n">cipher</span><span class="p">)))</span></code></pre></div> <p>A minimalistic python solution for this one was suggested by Niklas B. He makes use of <a href="http://docs.python.org/reference/expressions.html#lambda">Lambdas</a>, <a href="http://docs.python.org/library/stdtypes.html#str.translate">str.translate()</a> and <a href="http://docs.python.org/library/string.html#string.maketrans">str.maketrans()</a>:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">string</span> <span class="kn">as</span> <span class="nn">s</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="n">key</span> <span class="o">=</span> <span class="s">&quot;ynficwlbkuomxsevzpdrjgthaq&quot;</span> <span class="n">decode</span><span class="o">=</span> <span class="k">lambda</span> <span class="n">c</span><span class="p">:</span> <span class="n">s</span><span class="o">.</span><span class="n">translate</span><span class="p">(</span><span class="n">c</span><span class="p">,</span> <span class="n">s</span><span class="o">.</span><span class="n">maketrans</span><span class="p">(</span><span class="n">key</span><span class="p">,</span> <span class="n">s</span><span class="o">.</span><span class="n">ascii_lowercase</span><span class="p">))</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="k">print</span> <span class="n">decode</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">())</span></code></pre></div> <h2>Problem B: Dancing With the Googlers</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">ceil</span><span class="p">,</span> <span class="n">floor</span> <span class="k">def</span> <span class="nf">line2intlist</span><span class="p">(</span><span class="n">line</span><span class="p">):</span> <span class="nb">list</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">numbers</span> <span class="o">=</span> <span class="p">[</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span> <span class="p">]</span> <span class="k">return</span> <span class="n">numbers</span> <span class="k">def</span> <span class="nf">getDist</span><span class="p">(</span><span class="n">points</span><span class="p">,</span> <span class="n">isSurprising</span><span class="o">=</span><span class="bp">False</span><span class="p">):</span> <span class="n">p</span> <span class="o">=</span> <span class="n">floor</span><span class="p">(</span><span class="n">points</span> <span class="o">/</span> <span class="mf">3.0</span><span class="p">)</span> <span class="n">trip</span> <span class="o">=</span> <span class="p">[</span><span class="n">p</span><span class="p">,</span> <span class="n">p</span><span class="p">,</span> <span class="n">p</span><span class="p">]</span> <span class="k">if</span> <span class="mi">3</span><span class="o">*</span><span class="n">p</span> <span class="o">&lt;</span> <span class="n">points</span><span class="p">:</span> <span class="n">trip</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">if</span> <span class="p">(</span><span class="mi">3</span><span class="o">*</span><span class="n">p</span> <span class="o">+</span> <span class="mi">1</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">points</span><span class="p">:</span> <span class="n">trip</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">trip</span><span class="o">.</span><span class="n">sort</span><span class="p">(</span><span class="n">reverse</span><span class="o">=</span><span class="bp">True</span><span class="p">)</span> <span class="k">if</span> <span class="n">isSurprising</span> <span class="ow">and</span> <span class="p">(</span><span class="n">trip</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">==</span> <span class="n">trip</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="ow">and</span> <span class="n">trip</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">trip</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">-=</span> <span class="mi">1</span> <span class="n">trip</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">trip</span><span class="o">.</span><span class="n">sort</span><span class="p">(</span><span class="n">reverse</span><span class="o">=</span><span class="bp">True</span><span class="p">)</span> <span class="k">return</span> <span class="n">trip</span> <span class="k">def</span> <span class="nf">maxGooglers</span><span class="p">(</span><span class="n">nrOfGooglers</span><span class="p">,</span> <span class="n">surprising</span><span class="p">,</span> <span class="n">p</span><span class="p">,</span> <span class="n">points</span><span class="p">):</span> <span class="n">mg</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">surp</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">pi</span> <span class="ow">in</span> <span class="n">points</span><span class="p">:</span> <span class="n">trip</span> <span class="o">=</span> <span class="n">getDist</span><span class="p">(</span><span class="n">pi</span><span class="p">,</span> <span class="bp">True</span><span class="p">)</span> <span class="k">if</span> <span class="n">ceil</span><span class="p">(</span><span class="n">pi</span><span class="o">/</span><span class="mf">3.0</span><span class="p">)</span> <span class="o">&gt;=</span> <span class="n">p</span><span class="p">:</span> <span class="n">mg</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">elif</span> <span class="n">trip</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">&gt;=</span> <span class="n">p</span><span class="p">:</span> <span class="n">surp</span> <span class="o">+=</span> <span class="mi">1</span> <span class="n">mg</span> <span class="o">+=</span> <span class="nb">min</span><span class="p">(</span><span class="n">surp</span><span class="p">,</span> <span class="n">surprising</span><span class="p">)</span> <span class="k">return</span> <span class="n">mg</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">originalList</span> <span class="o">=</span> <span class="n">line2intlist</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">())</span> <span class="n">nrOfGooglers</span> <span class="o">=</span> <span class="n">originalList</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="n">surprising</span> <span class="o">=</span> <span class="n">originalList</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="n">p</span> <span class="o">=</span> <span class="n">originalList</span><span class="p">[</span><span class="mi">2</span><span class="p">]</span> <span class="n">points</span> <span class="o">=</span> <span class="n">originalList</span><span class="p">[</span><span class="mi">3</span><span class="p">:]</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">maxGooglers</span><span class="p">(</span><span class="n">nrOfGooglers</span><span class="p">,</span> <span class="n">surprising</span><span class="p">,</span> <span class="n">p</span><span class="p">,</span> <span class="n">points</span><span class="p">)))</span></code></pre></div> <h2>Problem C: Recycled Numbers</h2> <p>The small dataset of this one was easy, but I had to change my code a bit to make it work for the large dataset. Sadly, I didn’t know that I only have 8 minutes to get it work ☹</p> <p>I’ve tried cPickle for the 2,000,000 list. It took 128.7 MB and 1 minute 6.287s for the large data set after it was pickled. Without pickling it took 1 minute 31.900s.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">try</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">cPickle</span> <span class="kn">as</span> <span class="nn">pickle</span> <span class="k">except</span><span class="p">:</span> <span class="kn">import</span> <span class="nn">pickle</span> <span class="k">def</span> <span class="nf">line2intlist</span><span class="p">(</span><span class="n">line</span><span class="p">):</span> <span class="nb">list</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">numbers</span> <span class="o">=</span> <span class="p">[</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span> <span class="p">]</span> <span class="k">return</span> <span class="n">numbers</span> <span class="k">def</span> <span class="nf">binomialCoefficient</span><span class="p">(</span><span class="n">n</span><span class="p">,</span> <span class="n">k</span><span class="p">):</span> <span class="k">if</span> <span class="n">k</span> <span class="o">&lt;</span> <span class="mi">0</span> <span class="ow">or</span> <span class="n">k</span> <span class="o">&gt;</span> <span class="n">n</span><span class="p">:</span> <span class="k">return</span> <span class="mi">0</span> <span class="k">if</span> <span class="n">k</span> <span class="o">&gt;</span> <span class="n">n</span> <span class="o">-</span> <span class="n">k</span><span class="p">:</span> <span class="c"># take advantage of symmetry</span> <span class="n">k</span> <span class="o">=</span> <span class="n">n</span> <span class="o">-</span> <span class="n">k</span> <span class="n">c</span> <span class="o">=</span> <span class="mi">1</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">k</span><span class="p">):</span> <span class="n">c</span> <span class="o">=</span> <span class="n">c</span> <span class="o">*</span> <span class="p">(</span><span class="n">n</span> <span class="o">-</span> <span class="p">(</span><span class="n">k</span> <span class="o">-</span> <span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">)))</span> <span class="n">c</span> <span class="o">=</span> <span class="n">c</span> <span class="o">//</span> <span class="p">(</span><span class="n">i</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="k">return</span> <span class="n">c</span> <span class="c">#return n * (n - 1) / 2</span> <span class="k">def</span> <span class="nf">rot</span><span class="p">(</span><span class="n">num</span><span class="p">,</span> <span class="n">rot</span><span class="p">):</span> <span class="n">num</span> <span class="o">=</span> <span class="nb">str</span><span class="p">(</span><span class="n">num</span><span class="p">)</span> <span class="n">num</span> <span class="o">=</span> <span class="n">num</span><span class="p">[</span><span class="nb">len</span><span class="p">(</span><span class="n">num</span><span class="p">)</span><span class="o">-</span><span class="n">rot</span><span class="p">:</span><span class="nb">len</span><span class="p">(</span><span class="n">num</span><span class="p">)]</span> <span class="o">+</span> <span class="n">num</span><span class="p">[</span><span class="mi">0</span><span class="p">:</span><span class="nb">len</span><span class="p">(</span><span class="n">num</span><span class="p">)</span><span class="o">-</span><span class="n">rot</span><span class="p">]</span> <span class="k">return</span> <span class="nb">int</span><span class="p">(</span><span class="n">num</span><span class="p">)</span> <span class="k">def</span> <span class="nf">getRotList</span><span class="p">(</span><span class="n">num</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Only return bigger rotated ones &quot;&quot;&quot;</span> <span class="n">rotList</span> <span class="o">=</span> <span class="p">[</span><span class="n">num</span><span class="p">]</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">num</span><span class="p">))):</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">rot</span><span class="p">(</span><span class="n">num</span><span class="p">,</span> <span class="n">i</span><span class="p">)</span> <span class="k">if</span> <span class="n">tmp</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">rotList</span> <span class="ow">and</span> <span class="nb">len</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">tmp</span><span class="p">))</span> <span class="o">==</span> <span class="nb">len</span><span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">num</span><span class="p">)):</span> <span class="n">rotList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">tmp</span><span class="p">)</span> <span class="k">return</span> <span class="nb">sorted</span><span class="p">(</span><span class="n">rotList</span><span class="p">)</span> <span class="k">def</span> <span class="nf">inBorder</span><span class="p">(</span><span class="n">rotations</span><span class="p">,</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">):</span> <span class="n">count</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="n">rotations</span><span class="p">:</span> <span class="k">if</span> <span class="n">A</span> <span class="o">&lt;=</span> <span class="n">el</span> <span class="ow">and</span> <span class="n">el</span> <span class="o">&lt;=</span> <span class="n">B</span><span class="p">:</span> <span class="n">count</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">count</span> <span class="k">def</span> <span class="nf">recycled</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">liste</span><span class="p">):</span> <span class="n">pairs</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">minList</span> <span class="o">=</span> <span class="nb">range</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">B</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="k">for</span> <span class="n">tmpList</span> <span class="ow">in</span> <span class="n">liste</span><span class="p">[</span><span class="n">A</span><span class="p">:</span><span class="n">B</span><span class="o">+</span><span class="mi">1</span><span class="p">]:</span> <span class="k">if</span> <span class="n">minList</span><span class="p">[</span><span class="n">tmpList</span><span class="p">[</span><span class="mi">0</span><span class="p">]]:</span> <span class="n">nrInBorder</span> <span class="o">=</span> <span class="n">inBorder</span><span class="p">(</span><span class="n">tmpList</span><span class="p">,</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">)</span> <span class="n">pairs</span> <span class="o">+=</span> <span class="n">binomialCoefficient</span><span class="p">(</span><span class="n">nrInBorder</span><span class="p">,</span> <span class="mi">2</span><span class="p">)</span> <span class="n">minList</span><span class="p">[</span><span class="n">tmpList</span><span class="p">[</span><span class="mi">0</span><span class="p">]]</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">return</span> <span class="n">pairs</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">liste</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">try</span><span class="p">:</span> <span class="n">liste</span> <span class="o">=</span> <span class="n">pickle</span><span class="o">.</span><span class="n">load</span><span class="p">(</span><span class="nb">open</span><span class="p">(</span> <span class="s">&quot;save.p&quot;</span><span class="p">,</span> <span class="s">&quot;rb&quot;</span> <span class="p">))</span> <span class="k">except</span> <span class="ne">IOError</span><span class="p">:</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">2000001</span><span class="p">):</span> <span class="n">tmp</span> <span class="o">=</span> <span class="n">getRotList</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="n">liste</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">tmp</span><span class="p">)</span> <span class="n">pickle</span><span class="o">.</span><span class="n">dump</span><span class="p">(</span><span class="n">liste</span><span class="p">,</span> <span class="nb">open</span><span class="p">(</span> <span class="s">&quot;save.p&quot;</span><span class="p">,</span> <span class="s">&quot;wb&quot;</span> <span class="p">))</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">A</span><span class="p">,</span> <span class="n">B</span> <span class="o">=</span> <span class="n">line2intlist</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">())</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">recycled</span><span class="p">(</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span><span class="p">,</span> <span class="n">liste</span><span class="p">)))</span></code></pre></div> <h2>Problem D: Hall of Mirrors</h2> <p>This one was very hard. I had some ideas, but none of them seemed to work.</p> <p>This is a solution based on the solution of “dwenzel”. At the moment, I’ve only made some comments and broke some lines to let them fit into my blog. This solution needs about 2 minutes 42 seconds for the small input set and 2 minutes 12 seconds for the large input set.</p> <p>You might also be interested in the <a href="http://code.google.com/codejam/contest/1460488/dashboard#s=a&amp;a=3">official Contest Analysis</a> with some hints to this challenge.</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">floor</span><span class="p">,</span> <span class="n">ceil</span><span class="p">,</span> <span class="n">sqrt</span> <span class="n">precision</span> <span class="o">=</span> <span class="mf">0.01</span> <span class="k">def</span> <span class="nf">line2intlist</span><span class="p">(</span><span class="n">line</span><span class="p">):</span> <span class="nb">list</span> <span class="o">=</span> <span class="n">line</span><span class="o">.</span><span class="n">split</span><span class="p">(</span><span class="s">&#39; &#39;</span><span class="p">)</span> <span class="n">numbers</span> <span class="o">=</span> <span class="p">[</span> <span class="nb">int</span><span class="p">(</span><span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">list</span> <span class="p">]</span> <span class="k">return</span> <span class="n">numbers</span> <span class="k">def</span> <span class="nf">seeReflection</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">v</span><span class="p">,</span> <span class="n">m</span><span class="p">,</span> <span class="n">d</span><span class="p">):</span> <span class="n">cur_y</span> <span class="o">=</span> <span class="n">x</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="n">cur_x</span> <span class="o">=</span> <span class="n">x</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="n">vy</span> <span class="o">=</span> <span class="n">v</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="n">vx</span> <span class="o">=</span> <span class="n">v</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="n">dist</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">while</span> <span class="n">dist</span> <span class="o">&lt;=</span> <span class="n">d</span> <span class="o">+</span> <span class="n">precision</span><span class="p">:</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">cur_x</span> <span class="o">-</span> <span class="n">x</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span> <span class="o">&lt;</span> <span class="n">precision</span> <span class="ow">and</span> \ <span class="nb">abs</span><span class="p">(</span><span class="n">cur_y</span> <span class="o">-</span> <span class="n">x</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span> <span class="o">&lt;</span> <span class="n">precision</span> <span class="ow">and</span> <span class="n">dist</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">if</span> <span class="n">vy</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">if</span> <span class="n">vx</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">cur_x</span> <span class="o">-=</span> <span class="mf">0.5</span> <span class="k">else</span><span class="p">:</span> <span class="n">cur_x</span> <span class="o">+=</span> <span class="mf">0.5</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">cur_x</span> <span class="o">-</span> <span class="nb">round</span><span class="p">(</span><span class="n">cur_x</span><span class="p">))</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">floor</span><span class="p">(</span><span class="n">cur_y</span><span class="p">))</span> <span class="k">if</span> <span class="n">vx</span> <span class="o">&lt;</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">m</span><span class="p">[</span><span class="n">tmp</span><span class="p">][</span><span class="nb">int</span><span class="p">(</span><span class="nb">round</span><span class="p">(</span><span class="n">cur_x</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">vx</span> <span class="o">=</span> <span class="o">-</span><span class="n">vx</span> <span class="k">elif</span> <span class="n">vx</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">m</span><span class="p">[</span><span class="n">tmp</span><span class="p">][</span><span class="nb">int</span><span class="p">(</span><span class="nb">round</span><span class="p">(</span><span class="n">cur_x</span><span class="p">))]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">vx</span> <span class="o">=</span> <span class="o">-</span><span class="n">vx</span> <span class="n">dist</span> <span class="o">+=</span> <span class="mf">0.5</span> <span class="k">elif</span> <span class="n">vx</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">if</span> <span class="n">vy</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">cur_y</span> <span class="o">-=</span> <span class="mf">0.5</span> <span class="k">else</span><span class="p">:</span> <span class="n">cur_y</span> <span class="o">+=</span> <span class="mf">0.5</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">cur_y</span> <span class="o">-</span> <span class="nb">round</span><span class="p">(</span><span class="n">cur_y</span><span class="p">))</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="n">tmp</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">floor</span><span class="p">(</span><span class="n">cur_x</span><span class="p">))</span> <span class="k">if</span> <span class="n">vy</span> <span class="o">&lt;</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">m</span><span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="nb">round</span><span class="p">(</span><span class="n">cur_y</span><span class="p">)</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)][</span><span class="n">tmp</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">vy</span> <span class="o">=</span> <span class="o">-</span><span class="n">vy</span> <span class="k">elif</span> <span class="n">vy</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="ow">and</span> <span class="n">m</span><span class="p">[</span><span class="nb">int</span><span class="p">(</span><span class="nb">round</span><span class="p">(</span><span class="n">cur_y</span><span class="p">))][</span><span class="n">tmp</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">vy</span> <span class="o">=</span> <span class="o">-</span><span class="n">vy</span> <span class="n">dist</span> <span class="o">+=</span> <span class="mf">0.5</span> <span class="k">else</span><span class="p">:</span> <span class="c"># Find how far is the next time we hit something </span> <span class="c"># .0 or .5</span> <span class="k">if</span> <span class="n">vy</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">dy</span> <span class="o">=</span> <span class="n">cur_y</span> <span class="o">-</span> <span class="n">floor</span><span class="p">(</span><span class="n">cur_y</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">dy</span> <span class="o">=</span> <span class="n">ceil</span><span class="p">(</span><span class="n">cur_y</span><span class="p">)</span> <span class="o">-</span> <span class="n">cur_y</span> <span class="k">if</span> <span class="n">dy</span> <span class="o">&gt;</span> <span class="mf">0.5</span> <span class="o">+</span> <span class="n">precision</span><span class="p">:</span> <span class="n">dy</span> <span class="o">-=</span> <span class="mf">0.5</span> <span class="k">elif</span> <span class="n">dy</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="n">dy</span> <span class="o">+=</span> <span class="mf">0.5</span> <span class="k">if</span> <span class="n">vx</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">dx</span> <span class="o">=</span> <span class="n">cur_x</span> <span class="o">-</span> <span class="n">floor</span><span class="p">(</span><span class="n">cur_x</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">dx</span> <span class="o">=</span> <span class="n">ceil</span><span class="p">(</span><span class="n">cur_x</span><span class="p">)</span> <span class="o">-</span> <span class="n">cur_x</span> <span class="k">if</span> <span class="n">dx</span> <span class="o">&gt;</span> <span class="mf">0.5</span> <span class="o">+</span> <span class="n">precision</span><span class="p">:</span> <span class="n">dx</span> <span class="o">-=</span> <span class="mf">0.5</span> <span class="k">elif</span> <span class="n">dx</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="n">dx</span> <span class="o">+=</span> <span class="mf">0.5</span> <span class="c"># See which will come up first</span> <span class="n">ty</span> <span class="o">=</span> <span class="n">dy</span> <span class="o">/</span> <span class="nb">abs</span><span class="p">(</span><span class="n">vy</span><span class="p">)</span> <span class="n">tx</span> <span class="o">=</span> <span class="n">dx</span> <span class="o">/</span> <span class="nb">abs</span><span class="p">(</span><span class="n">vx</span><span class="p">)</span> <span class="k">if</span> <span class="n">ty</span> <span class="o">&gt;</span> <span class="n">tx</span><span class="p">:</span> <span class="n">t</span> <span class="o">=</span> <span class="n">tx</span> <span class="k">else</span><span class="p">:</span> <span class="n">t</span> <span class="o">=</span> <span class="n">ty</span> <span class="n">dy</span> <span class="o">=</span> <span class="n">vy</span> <span class="o">*</span> <span class="n">t</span> <span class="n">dx</span> <span class="o">=</span> <span class="n">vx</span> <span class="o">*</span> <span class="n">t</span> <span class="n">cur_y</span> <span class="o">=</span> <span class="n">cur_y</span> <span class="o">+</span> <span class="n">dy</span> <span class="n">cur_x</span> <span class="o">=</span> <span class="n">cur_x</span> <span class="o">+</span> <span class="n">dx</span> <span class="n">dist</span> <span class="o">+=</span> <span class="n">sqrt</span><span class="p">(</span><span class="n">dy</span> <span class="o">*</span> <span class="n">dy</span> <span class="o">+</span> <span class="n">dx</span> <span class="o">*</span> <span class="n">dx</span><span class="p">)</span> <span class="n">roundy</span> <span class="o">=</span> <span class="nb">round</span><span class="p">(</span><span class="n">cur_y</span><span class="p">)</span> <span class="n">roundx</span> <span class="o">=</span> <span class="nb">round</span><span class="p">(</span><span class="n">cur_x</span><span class="p">)</span> <span class="n">ybounce</span> <span class="o">=</span> <span class="bp">False</span> <span class="n">xbounce</span> <span class="o">=</span> <span class="bp">False</span> <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">cur_y</span> <span class="o">-</span> <span class="n">roundy</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">precision</span> <span class="ow">and</span> \ <span class="nb">abs</span><span class="p">(</span><span class="n">cur_x</span> <span class="o">-</span> <span class="n">roundx</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="c"># Case we&#39;re at a corner</span> <span class="n">neighbors</span> <span class="o">=</span> <span class="p">[]</span> <span class="n">intx</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">roundx</span><span class="p">)</span> <span class="n">inty</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">roundy</span><span class="p">)</span> <span class="n">neighbors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="n">inty</span> <span class="o">-</span> <span class="mi">1</span><span class="p">][</span><span class="n">intx</span> <span class="o">-</span> <span class="mi">1</span><span class="p">]</span> <span class="o">%</span> <span class="mi">2</span><span class="p">)</span> <span class="n">neighbors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="n">inty</span> <span class="o">-</span> <span class="mi">1</span><span class="p">][</span><span class="n">intx</span><span class="p">]</span> <span class="o">%</span> <span class="mi">2</span><span class="p">)</span> <span class="n">neighbors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="n">inty</span><span class="p">][</span><span class="n">intx</span><span class="p">]</span> <span class="o">%</span> <span class="mi">2</span><span class="p">)</span> <span class="n">neighbors</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">m</span><span class="p">[</span><span class="n">inty</span><span class="p">][</span><span class="n">intx</span> <span class="o">-</span> <span class="mi">1</span><span class="p">]</span> <span class="o">%</span> <span class="mi">2</span><span class="p">)</span> <span class="nb">sum</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">neighbor</span> <span class="ow">in</span> <span class="n">neighbors</span><span class="p">:</span> <span class="nb">sum</span> <span class="o">+=</span> <span class="n">neighbor</span> <span class="k">if</span> <span class="nb">sum</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">if</span> <span class="n">vy</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">nexty</span> <span class="o">=</span> <span class="n">inty</span> <span class="o">-</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="n">nexty</span> <span class="o">=</span> <span class="n">inty</span> <span class="k">if</span> <span class="n">vx</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">nextx</span> <span class="o">=</span> <span class="n">intx</span> <span class="o">-</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="n">nextx</span> <span class="o">=</span> <span class="n">intx</span> <span class="k">if</span> <span class="n">m</span><span class="p">[</span><span class="n">nexty</span><span class="p">][</span><span class="n">nextx</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">elif</span> <span class="nb">sum</span> <span class="o">==</span> <span class="mi">3</span><span class="p">:</span> <span class="n">vy</span> <span class="o">=</span> <span class="o">-</span><span class="n">vy</span> <span class="n">vx</span> <span class="o">=</span> <span class="o">-</span><span class="n">vx</span> <span class="k">elif</span> <span class="nb">sum</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span> <span class="k">if</span> <span class="n">neighbors</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">neighbors</span><span class="p">[</span><span class="mi">1</span><span class="p">]:</span> <span class="n">vy</span> <span class="o">=</span> <span class="o">-</span><span class="n">vy</span> <span class="k">elif</span> <span class="n">neighbors</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">==</span> <span class="n">neighbors</span><span class="p">[</span><span class="mi">3</span><span class="p">]:</span> <span class="n">vx</span> <span class="o">=</span> <span class="o">-</span><span class="n">vx</span> <span class="k">elif</span> <span class="nb">abs</span><span class="p">(</span><span class="n">cur_y</span> <span class="o">-</span> <span class="n">roundy</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="c"># Case we&#39;re middle of a top/bottom edge</span> <span class="k">if</span> <span class="n">vy</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">inty</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">roundy</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">inty</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">roundy</span><span class="p">)</span> <span class="n">intx</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">floor</span><span class="p">(</span><span class="n">cur_x</span><span class="p">))</span> <span class="k">if</span> <span class="n">m</span><span class="p">[</span><span class="n">inty</span><span class="p">][</span><span class="n">intx</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">vy</span> <span class="o">=</span> <span class="o">-</span><span class="n">vy</span> <span class="k">elif</span> <span class="nb">abs</span><span class="p">(</span><span class="n">cur_x</span> <span class="o">-</span> <span class="n">roundx</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">precision</span><span class="p">:</span> <span class="c"># Case we&#39;re middle of a top/bottom edge</span> <span class="k">if</span> <span class="n">vx</span> <span class="o">&lt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">intx</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">roundx</span> <span class="o">-</span> <span class="mi">1</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">intx</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">roundx</span><span class="p">)</span> <span class="n">inty</span> <span class="o">=</span> <span class="nb">int</span><span class="p">(</span><span class="n">floor</span><span class="p">(</span><span class="n">cur_y</span><span class="p">))</span> <span class="k">if</span> <span class="n">m</span><span class="p">[</span><span class="n">inty</span><span class="p">][</span><span class="n">intx</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="n">vx</span> <span class="o">=</span> <span class="o">-</span><span class="n">vx</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">def</span> <span class="nf">getMap</span><span class="p">(</span><span class="n">H</span><span class="p">,</span> <span class="n">W</span><span class="p">):</span> <span class="nb">map</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">el</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">H</span><span class="p">):</span> <span class="n">line</span> <span class="o">=</span> <span class="nb">raw_input</span><span class="p">()</span> <span class="n">tmp</span> <span class="o">=</span> <span class="p">[]</span> <span class="k">for</span> <span class="n">char</span> <span class="ow">in</span> <span class="n">line</span><span class="p">:</span> <span class="k">if</span> <span class="n">char</span> <span class="o">==</span> <span class="s">&#39;.&#39;</span><span class="p">:</span> <span class="n">tmp</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="mi">0</span><span class="p">)</span> <span class="k">elif</span> <span class="n">char</span> <span class="o">==</span> <span class="s">&#39;#&#39;</span><span class="p">:</span> <span class="n">tmp</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span> <span class="k">else</span><span class="p">:</span> <span class="n">tmp</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="mi">2</span><span class="p">)</span> <span class="nb">map</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">tmp</span><span class="p">)</span> <span class="k">return</span> <span class="nb">map</span> <span class="k">def</span> <span class="nf">process_case</span><span class="p">(</span><span class="n">m</span><span class="p">,</span> <span class="n">H</span><span class="p">,</span> <span class="n">W</span><span class="p">,</span> <span class="n">D</span><span class="p">):</span> <span class="n">vectors</span> <span class="o">=</span> <span class="nb">set</span><span class="p">()</span> <span class="n">ratios</span> <span class="o">=</span> <span class="nb">set</span><span class="p">()</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">D</span> <span class="o">+</span> <span class="mi">1</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">D</span> <span class="o">+</span> <span class="mi">1</span><span class="p">):</span> <span class="k">if</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="n">j</span> <span class="ow">and</span> <span class="n">i</span><span class="o">*</span><span class="n">i</span> <span class="o">+</span> <span class="n">j</span><span class="o">*</span><span class="n">j</span> <span class="o">&lt;=</span> <span class="n">D</span> <span class="o">*</span> <span class="n">D</span><span class="p">:</span> <span class="n">ratio</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="o">/</span> <span class="nb">float</span><span class="p">(</span><span class="n">j</span><span class="p">)</span> <span class="k">if</span> <span class="n">ratio</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">ratios</span><span class="p">:</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="n">i</span><span class="p">,</span> <span class="o">-</span><span class="n">j</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="o">-</span><span class="n">i</span><span class="p">,</span> <span class="n">j</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="o">-</span><span class="n">i</span><span class="p">,</span> <span class="o">-</span><span class="n">j</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="n">j</span><span class="p">,</span> <span class="n">i</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="n">j</span><span class="p">,</span> <span class="o">-</span><span class="n">i</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="o">-</span><span class="n">j</span><span class="p">,</span> <span class="n">i</span><span class="p">))</span> <span class="n">vectors</span><span class="o">.</span><span class="n">add</span><span class="p">((</span><span class="o">-</span><span class="n">j</span><span class="p">,</span> <span class="o">-</span><span class="n">i</span><span class="p">))</span> <span class="n">ratios</span><span class="o">.</span><span class="n">add</span><span class="p">(</span><span class="n">ratio</span><span class="p">)</span> <span class="n">x</span> <span class="o">=</span> <span class="bp">None</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">H</span><span class="p">):</span> <span class="k">for</span> <span class="n">j</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">W</span><span class="p">):</span> <span class="k">if</span> <span class="n">x</span> <span class="o">==</span> <span class="bp">None</span> <span class="ow">and</span> <span class="n">m</span><span class="p">[</span><span class="n">i</span><span class="p">][</span><span class="n">j</span><span class="p">]</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span> <span class="n">x</span> <span class="o">=</span> <span class="p">(</span><span class="n">i</span> <span class="o">+</span> <span class="mf">0.5</span><span class="p">,</span> <span class="n">j</span> <span class="o">+</span> <span class="mf">0.5</span><span class="p">)</span> <span class="n">count</span> <span class="o">=</span> <span class="mi">0</span> <span class="k">for</span> <span class="n">vector</span> <span class="ow">in</span> <span class="n">vectors</span><span class="p">:</span> <span class="k">if</span> <span class="n">seeReflection</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">vector</span><span class="p">,</span> <span class="n">m</span><span class="p">,</span> <span class="n">D</span><span class="p">):</span> <span class="n">count</span> <span class="o">+=</span> <span class="mi">1</span> <span class="k">return</span> <span class="n">count</span> <span class="k">if</span> <span class="n">__name__</span> <span class="o">==</span> <span class="s">&quot;__main__&quot;</span><span class="p">:</span> <span class="n">testcases</span> <span class="o">=</span> <span class="nb">input</span><span class="p">()</span> <span class="k">for</span> <span class="n">caseNr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="n">testcases</span><span class="p">):</span> <span class="n">H</span><span class="p">,</span> <span class="n">W</span><span class="p">,</span> <span class="n">D</span> <span class="o">=</span> <span class="n">line2intlist</span><span class="p">(</span><span class="nb">raw_input</span><span class="p">())</span> <span class="nb">map</span> <span class="o">=</span> <span class="n">getMap</span><span class="p">(</span><span class="n">H</span><span class="p">,</span> <span class="n">W</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Case #</span><span class="si">%i</span><span class="s">: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">caseNr</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">process_case</span><span class="p">(</span><span class="nb">map</span><span class="p">,</span> <span class="n">H</span><span class="p">,</span> <span class="n">W</span><span class="p">,</span> <span class="n">D</span><span class="p">)))</span></code></pre></div> <h2>See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/Google_Code_Jam">Google Code Jam</a></li> <li><a href="http://www.go-hero.net/jam/12/">Google Code Jam Statistics</a></li> </ul> PHP: A strange language //martin-thoma.com/php-a-strange-language/ Thu, 12 Apr 2012 16:24:32 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/php-a-strange-language <h2 id="automatic-conversion">Automatic conversion</h2> <h3 id="strings-to-numbers">Strings to numbers</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ php -a php &gt; <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#00D">123</span> == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">123ax</span><span style="color:#710">'</span></span>); <span style="color:#0a8;font-weight:bold">bool</span>(<span style="color:#069">true</span>) php &gt; <span style="color:#369;font-weight:bold">var_dump</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">123</span><span style="color:#710">'</span></span> == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">123ax</span><span style="color:#710">'</span></span>); <span style="color:#0a8;font-weight:bold">bool</span>(<span style="color:#069">false</span>) </pre></div> </div> </div> <h3 id="md5-hashes">MD5 hashes</h3> <div class="info">This one seems to be fixed. It doesn't work in PHP Version 5.4.6-1ubuntu1.2 (released 16.08.2012). It was a problem in PHP 5.3.5 (released 06.01.2011)</div> <p>PHP converts strings automatically to a float if it is possible. This might lead to problems. See this example from <a href="http://phpsadness.com/sad/47">phpsadness</a>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$password</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">ximaz</span><span style="color:#710">&quot;</span></span>; <span style="color:#950">$hash</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">61529519452809720693702583126814</span><span style="color:#710">&quot;</span></span>; <span style="color:#777">// = md5(&quot;ximaz&quot;)</span> <span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">md5</span>(<span style="color:#950">$password</span>) == <span style="color:#950">$hash</span>) { <span style="color:#369;font-weight:bold">print</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Allowed!</span><span style="color:#b0b">\n</span><span style="color:#710">&quot;</span></span>; } <span style="color:#950">$wrong_hash</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">61529519452809720000000000000000</span><span style="color:#710">&quot;</span></span>; <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$wrong_hash</span> == <span style="color:#950">$hash</span>) { <span style="color:#369;font-weight:bold">print</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Wrong hash got correct!</span><span style="color:#b0b">\n</span><span style="color:#710">&quot;</span></span>; } <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>See also:</p> <ul> <li><a href="http://php.net/language.operators.comparison">Comparison Operators</a></li> <li><a href="https://bugs.php.net/bug.php?id=54547">Bug #54547: wrong equality of string numbers</a></li> <li><a href="https://bugs.php.net/bug.php?id=62097">Bug #62097: New behavior of string == has a compatibility problem</a></li> <li><a href="http://de.wikipedia.org/wiki/Versionsgeschichte_von_PHP">Versionsgeschichte von PHP</a> (German)</li> </ul> <h2 id="inconsistency">Inconsistency</h2> <h3 id="starting-and-ending-php">Starting and ending PHP</h3> <p>The following snippet is valid PHP-code:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="font-weight:bold;color:#666">&lt;/script&gt;</span> ?<span style="color:#F00;background-color:#FAA">&gt;</span> </pre></div> </div> </div> <p>Source: <a href="http://stackoverflow.com/q/13228306/562769">StackOverflow.com</a> (You can find some explanations there.)</p> <h3 id="underscores">Underscores</h3> <p>Some functions use underscores between words, while others do not: <a href="http://php.net/gettype">gettype</a> vs. <a href="http://php.net/get_class">get_class</a></p> <h3 id="order-of-arguments">Order of Arguments</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#369;font-weight:bold">strpos</span> ( <span style="color:#0a8;font-weight:bold">string</span> <span style="color:#950">$haystack</span> , mixed <span style="color:#950">$needle</span> [...] ) <span style="color:#369;font-weight:bold">stristr</span> ( <span style="color:#0a8;font-weight:bold">string</span> <span style="color:#950">$haystack</span> , mixed <span style="color:#950">$needle</span> [...] ) <span style="color:#369;font-weight:bold">in_array</span> ( mixed <span style="color:#950">$needle</span> , <span style="color:#369;font-weight:bold">array</span> <span style="color:#950">$haystack</span> [...] ) <span style="color:#369;font-weight:bold">array_search</span> ( mixed <span style="color:#950">$needle</span> , <span style="color:#369;font-weight:bold">array</span> <span style="color:#950">$haystack</span> [...] ) </pre></div> </div> </div> <h2 id="sorting">Sorting</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">function</span> <span style="color:#06B;font-weight:bold">pivot</span>(<span style="color:#950">$arr</span>) { <span style="color:#080;font-weight:bold">return</span> (<span style="color:#950">$arr</span>[<span style="color:#00D">0</span>] + <span style="color:#369;font-weight:bold">end</span>(<span style="color:#950">$arr</span>)) / <span style="color:#00D">2</span>; } <span style="color:#950">$arr</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">1</span>, <span style="color:#00D">5</span>, <span style="color:#00D">7</span>, <span style="color:#00D">2</span>, <span style="color:#00D">3</span>, <span style="color:#00D">4</span>, <span style="color:#00D">8</span>, <span style="color:#00D">9</span>, <span style="color:#00D">6</span>); <span style="color:#369;font-weight:bold">echo</span> pivot(<span style="color:#369;font-weight:bold">sort</span>(<span style="color:#950">$arr</span>)); </pre></div> </div> </div> <p>This doesn’t work. If you don’t know why, you should take a look at <a href="http://php.net/manual/de/function.sort.php">sort</a>.</p> <h2 id="argument-order">Argument order</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#369;font-weight:bold">mktime</span> ([<span style="color:#950">$hour</span> [, <span style="color:#950">$minute</span> [, <span style="color:#950">$second</span> [, <span style="color:#950">$month</span> [, <span style="color:#950">$day</span> [, <span style="color:#950">$year</span> [, <span style="color:#950">$is_dst</span>]]]]]]]) </pre></div> </div> </div> <h2 id="arrayfill">array_fill</h2> <p><a href="http://php.net/manual/en/function.array-fill.php"><code>array_fill</code></a> doesn’t allow 0 as ``$number`.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$number</span> = <span style="color:#00D">2</span>; <span style="color:#950">$arr</span> = <span style="color:#369;font-weight:bold">array_fill</span>(<span style="color:#00D">0</span>, <span style="color:#950">$number</span>, <span style="color:#00D">42</span>); <span style="color:#369;font-weight:bold">print_r</span>(<span style="color:#950">$arr</span>); <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>Array ( [0] =&gt; 42 [1] =&gt; 42 )</p> <h2 id="strange-loop">Strange loop</h2> <p>Loops themselves should not change anything. So take a look at this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$array</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">foo</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">bar</span><span style="color:#710">'</span></span>); <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$array</span>); <span style="color:#080;font-weight:bold">foreach</span> (<span style="color:#950">$array</span> <span style="color:#080;font-weight:bold">as</span> &amp;amp;<span style="color:#950">$foo</span>); <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$array</span>); <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>Output:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>array(2) { [0]=&gt; string(3) &quot;foo&quot; [1]=&gt; string(3) &quot;bar&quot; } array(2) { [0]=&gt; string(3) &quot;foo&quot; [1]=&gt; &amp;amp;string(3) &quot;bar&quot; } </pre></div> </div> </div> <h2 id="boolean-evaluation">Boolean evaluation</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$a</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">7.1</span><span style="color:#710">'</span></span>); <span style="color:#950">$arr1</span> = <span style="color:#369;font-weight:bold">array</span>( <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">foo</span><span style="color:#710">'</span></span> =&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">foo</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">bar</span><span style="color:#710">'</span></span> =&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">bar</span><span style="color:#710">'</span></span>, ); <span style="color:#950">$arr2</span> = <span style="color:#369;font-weight:bold">array</span>( <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">bar</span><span style="color:#710">'</span></span> =&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">bar</span><span style="color:#710">'</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">foo</span><span style="color:#710">'</span></span> =&gt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">foo</span><span style="color:#710">'</span></span>, ); <span style="color:#080;font-weight:bold">if</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">a</span><span style="color:#710">&quot;</span></span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">This </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#069">true</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">is </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#00D">9</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">PHP. </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#00D">07</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Oktal </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#00D">010</span> == <span style="color:#00D">8</span> ) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">is </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">8</span><span style="color:#710">&quot;</span></span> == <span style="color:#00D">8</span> ) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">also </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">0</span>)) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">true. </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$x</span> = <span style="color:#00D">1</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Like </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">in_array</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">7.10</span><span style="color:#710">'</span></span>, <span style="color:#950">$a</span>)) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">that </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$arr1</span> == <span style="color:#950">$arr2</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">one </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#00D">0</span> == <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">x</span><span style="color:#710">'</span></span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">is true.</span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#710">&quot;</span></span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false </span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#00D">0</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false</span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#00D">08</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false</span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">array</span>()) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false</span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$x</span> = <span style="color:#00D">0</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false</span><span style="color:#710">&quot;</span></span>;} <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$arr1</span> === <span style="color:#950">$arr2</span>) {<span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">false</span><span style="color:#710">&quot;</span></span>;} <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <h2 id="make-a-guess">Make a Guess</h2> <p>Try to guess what the following prints:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$i</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">a</span><span style="color:#710">'</span></span>; <span style="color:#950">$i</span> &lt;= <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">z</span><span style="color:#710">'</span></span>; ++<span style="color:#950">$i</span>) <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#950">$i</span><span style="color:#D20"> </span><span style="color:#710">&quot;</span></span>; <span style="color:#777">// I just need four NULLs to demo this.</span> <span style="color:#950">$a</span> = <span style="color:#369;font-weight:bold">array_fill</span>(<span style="color:#00D">0</span>, <span style="color:#00D">4</span>, <span style="color:#069">NULL</span>); <span style="color:#950">$a</span>[<span style="color:#00D">0</span>]++; ++<span style="color:#950">$a</span>[<span style="color:#00D">1</span>]; <span style="color:#950">$a</span>[<span style="color:#00D">2</span>]--; --<span style="color:#950">$a</span>[<span style="color:#00D">3</span>]; <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$a</span>); <span style="color:#950">$b</span>[<span style="color:#00D">0</span>]++; ++<span style="color:#950">$b</span>[<span style="color:#00D">1</span>]; <span style="color:#950">$b</span>[<span style="color:#00D">2</span>]--; --<span style="color:#950">$b</span>[<span style="color:#00D">3</span>]; <span style="color:#369;font-weight:bold">var_dump</span>(<span style="color:#950">$b</span>); <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>Did you guess the following?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre> a b c d e f g h i j k l m n o p q r s t u v w x y z aa ab ac ad ae af ag ah ai aj ak al am an ao ap aq ar as at au av aw ax ay az ba bb bc bd be bf bg bh bi bj bk bl bm bn bo bp bq br bs bt bu bv bw bx by bz ca cb cc cd ce cf cg ch ci cj ck cl cm cn co cp cq cr cs ct cu cv cw cx cy cz da db dc dd de df dg dh di dj dk dl dm dn do dp dq dr ds dt du dv dw dx dy dz ea eb ec ed ee ef eg eh ei ej ek el em en eo ep eq er es et eu ev ew ex ey ez fa fb fc fd fe ff fg fh fi fj fk fl fm fn fo fp fq fr fs ft fu fv fw fx fy fz ga gb gc gd ge gf gg gh gi gj gk gl gm gn go gp gq gr gs gt gu gv gw gx gy gz ha hb hc hd he hf hg hh hi hj hk hl hm hn ho hp hq hr hs ht hu hv hw hx hy hz ia ib ic id ie if ig ih ii ij ik il im in io ip iq ir is it iu iv iw ix iy iz ja jb jc jd je jf jg jh ji jj jk jl jm jn jo jp jq jr js jt ju jv jw jx jy jz ka kb kc kd ke kf kg kh ki kj kk kl km kn ko kp kq kr ks kt ku kv kw kx ky kz la lb lc ld le lf lg lh li lj lk ll lm ln lo lp lq lr ls lt lu lv lw lx ly lz ma mb mc md me mf mg mh mi mj mk ml mm mn mo mp mq mr ms mt mu mv mw mx my mz na nb nc nd ne nf ng nh ni nj nk nl nm nn no np nq nr ns nt nu nv nw nx ny nz oa ob oc od oe of og oh oi oj ok ol om on oo op oq or os ot ou ov ow ox oy oz pa pb pc pd pe pf pg ph pi pj pk pl pm pn po pp pq pr ps pt pu pv pw px py pz qa qb qc qd qe qf qg qh qi qj qk ql qm qn qo qp qq qr qs qt qu qv qw qx qy qz ra rb rc rd re rf rg rh ri rj rk rl rm rn ro rp rq rr rs rt ru rv rw rx ry rz sa sb sc sd se sf sg sh si sj sk sl sm sn so sp sq sr ss st su sv sw sx sy sz ta tb tc td te tf tg th ti tj tk tl tm tn to tp tq tr ts tt tu tv tw tx ty tz ua ub uc ud ue uf ug uh ui uj uk ul um un uo up uq ur us ut uu uv uw ux uy uz va vb vc vd ve vf vg vh vi vj vk vl vm vn vo vp vq vr vs vt vu vv vw vx vy vz wa wb wc wd we wf wg wh wi wj wk wl wm wn wo wp wq wr ws wt wu wv ww wx wy wz xa xb xc xd xe xf xg xh xi xj xk xl xm xn xo xp xq xr xs xt xu xv xw xx xy xz ya yb yc yd ye yf yg yh yi yj yk yl ym yn yo yp yq yr ys yt yu yv yw yx yy yz array(4) { [0]=&gt; int(1) [1]=&gt; int(1) [2]=&gt; NULL [3]=&gt; NULL } array(4) { [0]=&gt; int(1) [1]=&gt; int(1) [2]=&gt; NULL [3]=&gt; NULL } </pre></div> </div> </div> <h2 id="function-names-are-not-case-sensitive">Function names are NOT case sensitive</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">function</span> <span style="color:#06B;font-weight:bold">add</span>(<span style="color:#950">$a</span>, <span style="color:#950">$b</span>) { <span style="color:#080;font-weight:bold">return</span> <span style="color:#950">$a</span> + <span style="color:#950">$b</span>; } <span style="color:#950">$foo</span> = add(<span style="color:#00D">1</span>, <span style="color:#00D">2</span>); <span style="color:#950">$Foo</span> = <span style="color:#036;font-weight:bold">Add</span>(<span style="color:#00D">3</span>, <span style="color:#00D">4</span>); <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">foo is </span><span style="color:#950">$foo</span><span style="color:#710">&quot;</span></span>; <span style="color:#777">// outputs foo is 3</span> <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Foo is </span><span style="color:#950">$Foo</span><span style="color:#710">&quot;</span></span>; <span style="color:#777">// outputs Foo is 7</span> </pre></div> </div> </div> <p>Source: <a href="http://stackoverflow.com/a/2006635/562769">StackOverflow</a></p> <h2 id="php-logo">PHP Logo</h2> <p>Add <code>?=PHPE9568F34-D428-11d2-A769-00AA001ACF42</code> to any PHP script and take a look at the output. For example at <a href="http://en.wikipedia.org/wiki/Main_Page?=PHPE9568F34-D428-11d2-A769-00AA001ACF42">Wikipedia</a>.</p> <h2 id="sources">Sources</h2> <ul> <li><a href="http://phpsadness.com/">phpsadness.com</a></li> <li><a href="http://me.veekun.com/blog/2012/04/09/php-a-fractal-of-bad-design/">PHP: a fractal of bad design</a> (thanks to <a href="http://www.knallisworld.de/blog/2012/04/11/herrlicher-php-rant/">knallisworld.de</a>)</li> <li><a href="http://www.phpwtf.org/">phpwtf.org</a></li> </ul> Project Euler: Problem 142 //martin-thoma.com/project-euler-problem-142/ Sun, 08 Apr 2012 22:40:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/project-euler-problem-142 <p><a href="http://en.wikipedia.org/wiki/Project_Euler">Project Euler</a> is a series of challenging mathematical/computer programming problems that will require more than just mathematical insights to solve. Although mathematics will help you arrive at elegant and efficient methods, the use of a computer and programming skills will be required to solve most problems.</p> <p>The motivation for starting Project Euler, and its continuation, is to provide a platform for the inquiring mind to delve into unfamiliar areas and learn new concepts in a fun and recreational context.</p> <p>Today, I would like to discuss problem 142. I’ve seen a <a href="http://blog.san-ss.com.ar/2011/12/project-euler-problem-142-solved.html">post from Santiago Alessandri</a>, so I liked to do the task by myself.</p> <p>The task is:</p> <blockquote>Find the smallest x + y + z with integers `$x &gt; y &gt; z &gt; 0$` such that x + y, x - y, x + z, x - z, y + z, y - z are all perfect squares.</blockquote> <p>I don’t want to post the solution (if you want to cheat, I guess you could easily Google it), but some thoughts that might help you to get in the right direction.</p> <h2>First thought: Brute-force</h2> <p><a href="http://en.wikipedia.org/wiki/Brute-force_search">Brute-force</a> is the easiest way that could give you the solution. So I wrote this piece of code:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">sys</span> <span class="kn">from</span> <span class="nn">math</span> <span class="kn">import</span> <span class="n">sqrt</span> <span class="k">def</span> <span class="nf">is_square</span><span class="p">(</span><span class="n">integer</span><span class="p">):</span> <span class="n">root</span> <span class="o">=</span> <span class="n">sqrt</span><span class="p">(</span><span class="n">integer</span><span class="p">)</span> <span class="k">if</span> <span class="nb">int</span><span class="p">(</span><span class="n">root</span> <span class="o">+</span> <span class="mf">0.5</span><span class="p">)</span> <span class="o">**</span> <span class="mi">2</span> <span class="o">==</span> <span class="n">integer</span><span class="p">:</span> <span class="k">return</span> <span class="bp">True</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="bp">False</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">3</span><span class="p">,</span><span class="mi">1000</span><span class="p">):</span> <span class="k">print</span> <span class="n">x</span> <span class="k">for</span> <span class="n">y</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">2</span><span class="p">,</span> <span class="n">x</span><span class="p">):</span> <span class="k">for</span> <span class="n">z</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">y</span><span class="p">):</span> <span class="k">if</span> <span class="p">(</span><span class="n">x</span> <span class="o">&gt;</span> <span class="n">y</span> <span class="ow">and</span> <span class="n">y</span> <span class="o">&gt;</span> <span class="n">z</span><span class="p">):</span> <span class="k">if</span> <span class="p">(</span><span class="n">is_square</span><span class="p">(</span><span class="n">x</span> <span class="o">+</span> <span class="n">y</span><span class="p">)</span> <span class="ow">and</span> <span class="n">is_square</span><span class="p">(</span><span class="n">x</span> <span class="o">-</span> <span class="n">y</span><span class="p">)</span> <span class="ow">and</span> <span class="n">is_square</span><span class="p">(</span><span class="n">x</span> <span class="o">+</span> <span class="n">z</span><span class="p">)</span> <span class="ow">and</span> <span class="n">is_square</span><span class="p">(</span><span class="n">x</span> <span class="o">-</span> <span class="n">z</span><span class="p">)</span> <span class="ow">and</span> <span class="n">is_square</span><span class="p">(</span><span class="n">y</span> <span class="o">+</span> <span class="n">z</span><span class="p">)</span> <span class="ow">and</span> <span class="n">is_square</span><span class="p">(</span><span class="n">y</span> <span class="o">-</span> <span class="n">z</span><span class="p">)):</span> <span class="k">print</span> <span class="p">(</span><span class="s">&quot;</span><span class="si">%i</span><span class="s"> - </span><span class="si">%i</span><span class="s"> - </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">z</span><span class="p">))</span> <span class="n">sys</span><span class="o">.</span><span class="n">exit</span><span class="p">()</span></code></pre></div> <p>This is quite fast until you reach about 500. So this is not a good way to solve it.</p> <h2>Apply some math</h2> <p>You can formalize the task like this: Find the smallest <code>$x, y, z \in \mathbb{N}$</code>, so that:</p> <ol> <li>`$x &gt; y &gt; z &gt; 0$`</li> <li>`$a = x + y$`</li> <li>`$b = x - y$`</li> <li>`$c = x + z$`</li> <li>`$d = x - z$`</li> <li>`$e = y + z$`</li> <li>`$f = y - z$`</li> </ol> <p>With <code>$a, b, c, d, e, f \in Squares$</code>.</p> <p>Now you can make the following conclusions:</p> <ol> <li>`$\overset{A.1, A.2, A.3}{\implies} a &gt; b$`</li> <li>`$\overset{A.1, A.4, A.5}{\implies} c &gt; d$`</li> <li>`$\overset{A.1, A.6, A.7}{\implies} e &gt; f$`</li> </ol> <ol> <li> <p><code>$a &gt; c$</code>: <code>$y &gt; z$</code> <code>$\Leftrightarrow x + y &gt; x + z$</code> <code>$\Leftrightarrow a &gt; c$</code></p> </li> <li> <p><code>$c &gt; e$</code>: <code>$x &gt; y$</code> <code>$\Leftrightarrow x + z &gt; y + z$</code> <code>$c &gt; e$</code></p> </li> <li> <p>a is the biggest element (see B.1, B.4, B.6)</p> </li> <li> <p><code>$b &lt; c$</code>: <code>$-y &lt; z$</code> <code>$\Leftrightarrow x - y &lt; x + z$</code> <code>$b &lt; c$</code></p> </li> <li> <p>c is the second biggest element (see B.7, B.2, B.5, B.8)</p> </li> <li> <p><code>$b &lt; d$</code>: <code>$ y &gt; z$</code> <code>$\Leftrightarrow -y &lt; -z$</code> <code>$\Leftrightarrow x - y &lt; x - z$</code> <code>$b &lt; d$</code></p> </li> <li> <p><code>$d &gt; f$</code>: <code>$ x &gt; y$</code> <code>$\Leftrightarrow x - z &gt; y - z$</code> <code>$d &gt; f$</code></p> </li> <li> <p>I can’t tell anything about the relationship between:</p> </li> </ol> <ul> <li>d and e</li> <li>b and f</li> <li>b and e</li> </ul> <p>Lets conclude:</p> <div style="width: 308px" class="wp-caption aligncenter"><a href="../images/2012/04/euler-142-graph.png"><img src="../images/2012/04/euler-142-graph.png" alt="Graph that visualizes the situation of the squares of Euler 142" width="" height="" class="size-full wp-image-21421" /></a><p class="wp-caption-text">Graph that visualizes the situation of the squares of Euler 142</p></div> <p>You also know:</p> <p><code>$x = \frac{a - b}{2} \implies \text{ (a - b) has to be even} \implies \text{a and b have the same parity.}$</code> The same argumentation can be used for (c, d) and (e, f).</p> <p><code>$x &gt; y &gt; z &gt; 0 \land a = x + y \implies a \geq 5$</code>.</p> <p>With this in mind you don’t have to loop over three variables but only over two. This is much faster. As z is over 1000 you need it. My new script took about 1.5 minutes.</p> <h2>Material</h2> <p>Some material like the LaTeX-file can be found in the <a href="../images/2012/04/euler-142.zip">Project Euler 142 Archive</a>.</p> The Best Advertising Campaigns //martin-thoma.com/the-best-advertising-campaigns/ Sun, 08 Apr 2012 22:15:57 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/the-best-advertising-campaigns <h2>Jobs in Town</h2> <table> <tr> <td> <img src="../images/2012/04/jobs-in-town-bankautomat.jpg" alt="Jobs in Town Advertising (Bankautomat)" title="Jobs in Town Advertising (Bankautomat)" width="250" height="366" class="size-full wp-image-21571" /> </td> <td> <img src="../images/2012/04/jobs-in-town-eismaschine.jpg" alt="Jobs in Town Advertising (Eismaschine)" title="Jobs in Town Advertising (Eismaschine)" width="250" height="350" class="size-full wp-image-21581" /></td> </tr> <tr> <td> <img src="../images/2012/04/jobs-in-town-kaffeeautomat.jpg" alt="Jobs in Town Advertising (Kaffeeautomat)" title="Jobs in Town Advertising (Kaffeeautomat)" width="250" height="353" class="size-full wp-image-21591" /></td> <td> <img src="../images/2012/04/jobs-in-town-kinderauto.jpg" alt="Jobs in Town Advertising (Kinderauto)" title="Jobs in Town Advertising (Kinderauto)" width="250" height="345" class="size-full wp-image-21601" /></td> </tr> <tr> <td> <img src="../images/2012/04/jobs-in-town-music-machine-ad.jpg" alt="Jobs in Town Advertising (Music Machine)" title="Jobs in Town Advertising (Music Machine)" width="250" height="344" class="size-full wp-image-21611" /></td> <td> <img src="../images/2012/04/jobs-in-town-tankstelle.jpg" alt="Jobs in Town Advertising (Tankstelle)" title="Jobs in Town Advertising (Tankstelle)" width="250" height="351" class="size-full wp-image-21621" /></td> </tr> <tr> <td colspan="2"> <img src="../images/2012/04/jobs-in-town-washing-machine.jpg" alt="Jobs in Town Advertising (Waschmaschine)" title="Jobs in Town Advertising (Waschmaschine)" width="425" height="302" class="size-full wp-image-21631" /></td> </tr> </table> <h2>FedEx</h2> <div style="width: 420px" class="wp-caption aligncenter"><a href="../images/2012/04/fedex-ad.jpg"><img src="../images/2012/04/fedex-ad.jpg" alt="FedEx vs UPS" width="" height="" class="size-full wp-image-21661" /></a><p class="wp-caption-text">FedEx vs UPS</p></div> <h2>Mr. Clean</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/mr-clean-ad.jpg"><img src="../images/2012/04/mr-clean-ad.jpg" alt="Mr. Clean Advertising" width="" height="" class="size-full wp-image-21671" /></a><p class="wp-caption-text">Mr. Clean Advertising</p></div> <h2>Tip Ex</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/tipex-ad.jpg"><img src="../images/2012/04/tipex-ad.jpg" alt="TipEx advertising" width="" height="" class="size-full wp-image-21691" /></a><p class="wp-caption-text">TipEx advertising</p></div> <h2>National Geographic Channel</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/national-geographic-channel-ad.png"><img src="../images/2012/04/national-geographic-channel-ad.png" alt="National Geographic Channel Advertising" width="" height="" class="size-full wp-image-21681" /></a><p class="wp-caption-text">National Geographic Channel Advertising</p></div> <h2>Tampax</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/tampax-ad.jpg"><img src="../images/2012/04/tampax-ad.jpg" alt="Tampax advertising" width="" height="" class="size-full wp-image-21701" /></a><p class="wp-caption-text">Tampax advertising</p></div> <h2>3M Security Glass</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/3m-ad.jpg"><img src="../images/2012/04/3m-ad.jpg" alt="3M Security Glass" width="" height="" class="size-full wp-image-21711" /></a><p class="wp-caption-text">3M Security Glass</p></div> <h2>Coffee</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/coffee-ad.jpg"><img src="../images/2012/04/coffee-ad.jpg" alt="Coffee advertising" width="" height="" class="size-full wp-image-21721" /></a><p class="wp-caption-text">Coffee advertising</p></div> <h2>Funeral ad</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/funeral-ad.jpg"><img src="../images/2012/04/funeral-ad.jpg" alt="Funeral advertising" width="" height="" class="size-full wp-image-21731" /></a><p class="wp-caption-text">Funeral advertising</p></div> <h2>Ravensburger</h2> <div style="width: 435px" class="wp-caption aligncenter"><a href="../images/2012/04/ravensburger-puzzle-ad.jpg"><img src="../images/2012/04/ravensburger-puzzle-ad.jpg" alt="Ravensburger Puzzle advertising" width="" height="" class="size-full wp-image-21751" /></a><p class="wp-caption-text">Ravensburger Puzzle advertising</p></div> Amazing Animals //martin-thoma.com/amazing-animals/ Sat, 07 Apr 2012 02:39:26 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/amazing-animals <p>Some animals are truly amazing. Just take a look at them. I’ve also included some video clips of funny individuals.</p> <h2>Axoltotl</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/axolotl-300x269.jpg"><img src="../images/2012/04/axolotl-300x269.jpg" alt="Axoltol" width="" height="" class="size-medium wp-image-21171" /></a><p class="wp-caption-text">Axoltol</p></div> <p>The <a href="http://en.wikipedia.org/wiki/Axolotl">axoltotl</a> is capable of the <strong>regeneration</strong> of entire lost appendages in a period of months, and, in certain cases, more vital structures. Some have indeed been found restoring the less vital parts of their brains. They can also readily accept transplants from other individuals, including eyes and parts of the brain—restoring these alien organs to full functionality. In some cases, axolotls have been known to repair a damaged limb as well as regenerating an additional one, ending up with an extra appendage that makes them attractive to pet owners as a novelty. In metamorphosed individuals, however, the ability to regenerate is greatly diminished. The axolotl is therefore used as a model for the development of limbs in vertebrates.</p> <h2>Platypus</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/Platypus-300x201.jpg"><img src="../images/2012/04/Platypus-300x201.jpg" alt="Platypus" width="" height="" class="size-medium wp-image-21181" /></a><p class="wp-caption-text">Platypus</p></div> <p>Together with the four species of echidna, the <a href="http://en.wikipedia.org/wiki/Platypus">platypus</a> is one of the five extant species of monotremes, the only <strong>mammals that lay eggs</strong> instead of giving birth to live young. It is one of the few <a href="http://en.wikipedia.org/wiki/Venomous_mammals">venomous mammals</a>.</p> <h2>Mimic Octopus</h2> <iframe width="512" height="377" src="http://www.youtube.com/embed/H8oQBYw6xxc" frameborder="0" allowfullscreen=""></iframe> <p>The <a href="http://en.wikipedia.org/wiki/Mimic_Octopus">mimic octopus</a> has a strong ability to mimic other creatures. It grows up to 60 cm (2 feet) in length. Its normal colouring consists of brown and white stripes or spots.</p> <h2>Lyrebird</h2> <iframe width="512" height="377" src="http://www.youtube.com/embed/VjE0Kdfos4Y" frameborder="0" allowfullscreen=""></iframe> <p>A Lyrebirds are most notable for their <strong>superb ability to mimic natural and artificial sounds</strong> from their environment. Lyrebirds have unique plumes of neutral coloured tailfeathers.</p> <h2>Chimpanzee</h2> <iframe width="512" height="290" src="http://www.youtube.com/embed/zJAH4ZJBiN8" frameborder="0" allowfullscreen=""></iframe> <h2>Ants</h2> <iframe width="512" height="384" src="http://www.youtube.com/embed/lFg21x2sj-M" frameborder="0" allowfullscreen=""></iframe> <h2>Individuals</h2> <h3>Einstein le perroquet</h3> <iframe width="512" height="377" src="http://www.youtube.com/embed/GRUgjMGLr5g" frameborder="0" allowfullscreen=""></iframe> <h3>Dog, Cat and Rat</h3> <iframe width="512" height="290" src="http://www.youtube.com/embed/D85yrIgA4Nk" frameborder="0" allowfullscreen=""></iframe> <h3>Genius dog climbs fence</h3> <iframe width="512" height="377" src="http://www.youtube.com/embed/MLssW7lyzxw" frameborder="0" allowfullscreen=""></iframe> <h3>Cat gets caught barking</h3> <iframe width="512" height="377" src="http://www.youtube.com/embed/aP3gzee1cps" frameborder="0" allowfullscreen=""></iframe> How Chrome could be improved //martin-thoma.com/how-chrome-could-be-improved/ Fri, 06 Apr 2012 14:19:31 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-chrome-could-be-improved <p>Google Chorme is the browser of my choice. It is fast, has developer tools and looks great. But it could be improved. I’ll describe some features I miss.</p> <h2>Disable sound for tabs</h2> <p>Sometimes I watch a movie while I play a flash game. Some flash games don’t offer an option to mute them. So I would like to get the possibility to disable sound for one tab.</p> <p>It could look like this.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/disable-tab-sound-300x172.png"><img src="../images/2012/04/disable-tab-sound-300x172.png" alt="Disable the sound of a tab" width="" height="" class="size-medium wp-image-20981" /></a><p class="wp-caption-text">Disable the sound of a tab</p></div> <h2>Spell checker</h2> <p>I write Blogs in German and in English. So I would like a spell-checker option at the bottom-left corner to switch languages:</p> <div style="width: 708px" class="wp-caption aligncenter"><a href="../images/2012/04/spell-checker.png"><img src="../images/2012/04/spell-checker.png" alt="Spell checker" width="" height="" class="size-full wp-image-21021" /></a><p class="wp-caption-text">Spell checker</p></div> <h2>HTML5 Form Elements</h2> <p>HTML5 brought many cool new form elements to the web. If you like, take a look at <a href="http://www.martin-thoma.de/html5/input.php">my list of HTML5 input types</a>. Chrome should support all of them! Note that Chrome does support these types according to <a href="http://html5test.com/">html5test.com</a>. But I can’t see any difference between type=url and type=text. That’s not supporting the new types!</p> <p>By the way, at the moment Chrome scores 385 points + 13 bonus points. The best browser currently scores 425 points + 25 bonus points.</p> <div style="width: 182px" class="wp-caption aligncenter"><a href="../images/2012/04/opera-11.01-date.png"><img src="../images/2012/04/opera-11.01-date.png" alt="Opera 11.01 Native date input type" width="" height="" class="size-full wp-image-21051" /></a><p class="wp-caption-text">Opera 11.01 Native date input type</p></div> <h2>Internal PDF-Reader</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/internal-pdf-reader-300x218.png"><img src="../images/2012/04/internal-pdf-reader-300x218.png" alt="Internal PDF reader of Chrome" width="" height="" class="size-medium wp-image-21001" /></a><p class="wp-caption-text">Internal PDF reader of Chrome</p></div> <h3>Rotate PDF</h3> <p>Some PDF files I receive are rotated by 90°. It would be great if I could, as in every PDF viewer, rotate this. A common shortcut is Ctrl+Arrow key.</p> <h3>Page numbers</h3> <p>It would be great, if I could enter the number of the page I want to view. For example in the URL by adding “#123” for page 123.</p> <h2>Security</h2> <h3>Extensions</h3> <p>Auto-Disable extensions for https. Only PayPal, Amazon, Ebay, GMail and my bank accounts work with https. I don’t need my Addons for these sites and I would appreciate if I could auto-disable them for https.</p> <h3>Password Reuse Visualizer</h3> <p>Firefox offers a tool which helps to identify passwords, that get reused often. It is called “<a href="https://addons.mozilla.org/de/firefox/addon/password-reuse-visualizer/">Password Reuse Visualizer</a>” and looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/04/password-reuse.png"><img src="../images/2012/04/password-reuse.png" alt="Password Reuse Visualizer" width="" height="" class="size-full wp-image-21101" /></a><p class="wp-caption-text">Password Reuse Visualizer</p></div> <h2>Material</h2> <p>I’ve used <a href="http://www.famfamfam.com/lab/icons/silk/">famfamfam slik icons</a>. For the menus I’ve used Sans, 14pt, no hinting but Antialiasing. If someone has better options, it would be great if you posted it as a comment.</p> <p>If you just want to see if your problem has already been submitted, go to the <a href="http://code.google.com/p/chromium/issues/list">issue-list</a>.</p> Wie berechne ich das multiplikativ Inverse einer komplexen Zahl? //martin-thoma.com/wie-berechne-ich-das-multiplikativ-inverse-einer-komplexen-zahl/ Wed, 04 Apr 2012 16:57:06 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-berechne-ich-das-multiplikativ-inverse-einer-komplexen-zahl <p>Im Folgenden werde ich kurz und bündig erklären, wie man das multiplikativ Inverse einer komplexen Zahl berechnet.</p> <h2>Beispiel</h2> <p>Berechne das multiplikativ Inverse zur komplexen Zahl <code>$(\frac{1}{10} + \frac{1}{5}i)$</code>.</p> <p>Das Ergebnis ist von der Form <code>$(c + di) \in \mathbb{C}$</code>. Es muss folgende Gleichung erfüllen: <a id="more"></a><a id="more-20591"></a> <code>$(\frac{1}{10} + \frac{1}{5}i) \cdot (c + di) = 1$</code> <code>$\Leftrightarrow (\frac{1}{10} \cdot c - \frac{1}{5} d) + (\frac{1}{5} c + \frac{1}{10} d)i = 1$</code> <code>$\Leftrightarrow (\frac{1}{10} \cdot c - \frac{1}{5} d) = 1 \land (\frac{1}{5} c + \frac{1}{10} d) = 0$</code> <code>$\Leftrightarrow \left( \begin{array}{c c | c} \frac{1}{10} &amp; -\frac{1}{5} &amp; 1 \\ \frac{1}{5} &amp; \frac{1}{10} &amp; 0 \end{array} \right) \Leftrightarrow \left( \begin{array}{c c | c} \frac{1}{10} &amp; -\frac{1}{5} &amp; 1 \\ 0 &amp; \frac{1+4}{10} &amp; -2 \end{array} \right) = \left( \begin{array}{c c | c} \frac{1}{10} &amp; -\frac{1}{5} &amp; 1 \\ 0 &amp; \frac{1}{2} &amp; -2 \end{array} \right)$</code> <code>$\Leftrightarrow \left( \begin{array}{c c | c} \frac{1}{10} &amp; -\frac{1}{5} &amp; 1 \\ 0 &amp; 1 &amp; -4 \end{array} \right) \Leftrightarrow \left( \begin{array}{c c | c} \frac{1}{10} &amp; 0 &amp; 1 - \frac{4}{5} \\ 0 &amp; 1 &amp; -4 \end{array} \right) = \left( \begin{array}{c c | c} \frac{1}{10} &amp; 0 &amp; \frac{1}{5} \\ 0 &amp; 1 &amp; -4 \end{array} \right)$</code> <code>$\Leftrightarrow \left( \begin{array}{c c | c} 1 &amp; 0 &amp; 2 \\ 0 &amp; 1 &amp; -4 \end{array} \right)$</code></p> <p>Das Ergebnis lautet also: Das multiplikativ Inverse zu <code>$(\frac{1}{10} + \frac{1}{5}i)$</code> ist <code>$(2 -4i)$</code>.</p> <h2>Allgemein</h2> <p>Berechne das multiplikativ Inverse zur komplexen Zahl <code>$(a + bi)$</code>.</p> <p>Das Ergebnis ist von der Form <code>$(c + di) \in \mathbb{C}$</code>. Es muss folgende Gleichung erfüllen: <code>$(a + bi) \cdot (c + di) = 1$</code> <code>$\Leftrightarrow (a c - b d) + (b c + a d)i = 1$</code> <code>$\Leftrightarrow (a c - b d) = 1 \land (b c + a d) = 0$</code></p> <h3>Fall 1: a ungleich 0</h3> <p><code>$\Leftrightarrow \left( \begin{array}{c c | c} a &amp; -b &amp; 1 \\ b &amp; a &amp; 0 \end{array} \right) \Leftrightarrow \left( \begin{array}{c c | c} a &amp; -b &amp; 1 \\ 0 &amp; a + \frac{b^2}{a} &amp; - \frac{b}{a} \end{array} \right) = \left( \begin{array}{c c | c} a &amp; -b &amp; 1 \\ 0 &amp; \frac{a^2 + b^2}{a} &amp; - \frac{b}{a} \end{array} \right)$</code> <code>$\Leftrightarrow \left( \begin{array}{c c | c} a &amp; -b &amp; 1 \\ 0 &amp; 1 &amp; -\frac{b}{a^2 + b^2} \end{array} \right) \Leftrightarrow \left( \begin{array}{c c | c} a &amp; 0 &amp; 1 - \frac{b^2}{a^2 + b^2} \\ 0 &amp; 1 &amp; -\frac{b}{a^2 + b^2} \end{array} \right) \Leftrightarrow \left( \begin{array}{c c | c} 1 &amp; 0 &amp; (1 - \frac{b^2}{a^2 + b^2})/a \\ 0 &amp; 1 &amp; -\frac{b}{a^2 + b^2} \end{array} \right)$</code> <code>$= \left( \begin{array}{c c | c} 1 &amp; 0 &amp; (\frac{a^2 + b^2 - b^2}{a^2 + b^2})/a \\ 0 &amp; 1 &amp; -\frac{b}{a^2 + b^2} \end{array} \right) = \left( \begin{array}{c c | c} 1 &amp; 0 &amp; \frac{a}{a^2 + b^2} \\ 0 &amp; 1 &amp; -\frac{b}{a^2 + b^2} \end{array} \right)$</code></p> <p>Das Ergebnis lautet also: Das multiplikativ Inverse zu <code>$(a + bi)$</code> ist also in diesem Fall <code>$(\frac{a}{a^2 + b^2} - \frac{b}{a^2 + b^2}i)$</code>.</p> <h3>Fall a gleich 0</h3> <p><code>$\Leftrightarrow - b d = 1 \land b c= 0$</code> <code>$\implies c = 0 \land d = - \frac{1}{b}$</code></p> <p>Das multiplikativ Inverse zu <code>$(bi)$</code> ist also in diesem Fall <code>$(0 - \frac{1}{b}i)$</code> = (\frac{0}{0^2 + b^2} - \frac{b}{0^2 + b^2}i)`$.</p> <h3>Ergebnis</h3> <p>Ganz allgemein kann man für das multiplikativ Inverse einer beliebigen komplexen Zahl also folgendes Angeben: $`(\frac{a}{a^2 + b^2} - \frac{b}{a^2 + b^2}i)$.</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Komplexe_Zahl">Komplexe Zahlen</a>, <a href="http://de.wikipedia.org/wiki/Inverses_Element">Inverses Element</a></li> </ul> How to install the latest LaTeX Version //martin-thoma.com/how-to-install-the-latest-latex-version/ Wed, 28 Mar 2012 11:29:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-install-the-latest-latex-version <p>I recently had <a href="http://tex.stackexchange.com/questions/49543/how-can-i-place-numbers-into-marks-of-a-plot">some problems</a> with TikZ because of my outdated LaTeX-Version. Ubuntu does only provide TeX Live 2009. The latest one is TeX Live 2013. As Ubuntu doesn’t provide the latest LaTeX-Code, I’ll explain how to install it by yourself on an Ubuntu System.</p> <h2 id="what-is-latex">What is LaTeX?</h2> <p>LaTeX is a document markup language. So with LaTeX you’re able to write math formula like <code>$\sum_{i=0}^\infty \frac{1}{2^i} = 2$</code>. The term LaTeX refers only to the language in which documents are written, not to the editor used to write those documents. In order to create a document in LaTeX, a .tex file must be created using some form of text editor. While most text editors can be used to create a LaTeX document, a number of editors have been created specifically for working with LaTeX.</p> <p>A number of TeX distributions are available, including TeX Live (multiplatform) and MiKTeX (Windows). When I write “LaTeX” I think of “TeX Live”.</p> <h2 id="latex-an-hello-world-example">LaTeX: an Hello World example</h2> <p>This is the template I use when I want to write a minimal LaTeX PDF document. You can use it as an example.</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,10pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage{amsthm} % needed for proof environment \usepackage[utf8]{inputenc} % this is needed for umlauts \usepackage[ngerman]{babel} % this is needed for umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage{geometry} \geometry{top=1cm,left=1cm,right=1cm,bottom=1cm} \pdfinfo{ /Author (Martin Thoma) /Title (Analysis I) /Subject (Analysis I) /Keywords (Analysis I; Venn-Diagramm) } \newtheorem*{vor}{Voraussetzung} \newtheorem*{beh}{Behauptung} \begin{document} \section{Hello World} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. \subsection{This is an subsection} Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est Lorem ipsum dolor sit amet. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse molestie consequat, vel illum dolore eu feugiat nulla facilisis at vero eros et accumsan et iusto odio dignissim qui blandit praesent luptatum zzril delenit augue duis dolore te feugait nulla facilisi. Lorem ipsum dolor sit amet, consectetuer adipiscing elit, sed diam nonummy nibh euismod tincidunt ut laoreet dolore magna aliquam erat volutpat. Ut wisi enim ad minim veniam, quis nostrud exerci tation ullamcorper suscipit lobortis nisl ut aliquip ex ea commodo consequat. Duis autem vel eum iriure dolor in hendrerit in vulputate velit esse \end{document} </pre></div> </div> </div> <p>If LaTeX is available on your system, you can create the PDF file from this myDocument.tex file with this command:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pdflatex myDocument.tex -output-format=pdf </pre></div> </div> </div> <p>This will create a .log file, an .aux file</p> <p>Here is the <a href="../images/2012/03/latex-template.zip">LaTeX template</a> with the resulting PDF.</p> <h2 id="install-the-latest-latex">Install the latest LaTeX</h2> <div class="important">Follow the instructions on <a href="http://tug.org/texlive/acquire-netinstall.html">tug.org</a>.</div> <p>It’s a Network installation, so it will need Internet access. It needs to download about 2 GB so it will take some time. But everything is done automatically.</p> <p>You should remove your old installation before you start the new one:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>sudo apt-get purge texlive-* sudo apt-get autoremove </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>wget http://mirror.ctan.org/systems/texlive/tlnet/install-tl-unx.tar.gz tar -zxvf install-tl-unx.tar.gz cd install-tl-* sudo ./install-tl I </pre></div> </div> </div> <p>After you’ve started your installation, you can choose options (O). Then you should choose “create symlinks in standard directories” (L).</p> <p>If you didn’t do so, add the path to your PATH (See <a href="http://askubuntu.com/a/60221/10425">How to add a directory to my path?</a>, <a href="http://askubuntu.com/a/60769/10425">How do I add a directory to MANPATH or INFOPATH?</a> and <a href="http://askubuntu.com/a/59127/10425">Reload .profile</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>PATH=$PATH:/usr/local/texlive/2013/bin/i386-linux/ </pre></div> </div> </div> <p>That’s it. So my <code>.profile</code> got these additional lines:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>if [ -d &quot;/usr/local/texlive/2013/bin/i386-linux&quot; ] ; then PATH=&quot;/usr/local/texlive/2013/bin/i386-linux:$PATH&quot; fi if [ -d &quot;/usr/local/texlive/2013/bin/x86_64-linux&quot; ] ; then PATH=&quot;/usr/local/texlive/2013/bin/x86_64-linux:$PATH&quot; fi if [ -d &quot;/usr/local/texlive/2013/texmf/doc/man&quot; ] ; then MANPATH=&quot;/usr/local/texlive/2013/texmf/doc/man:$MANPATH&quot; fi if [ -d &quot;/usr/local/texlive/2013/texmf/doc/info&quot; ] ; then INFOPATH=&quot;/usr/local/texlive/2013/texmf/doc/info:$INFOPATH&quot; fi </pre></div> </div> </div> <p>edit: I’ve just installed TeX-Live 2013 and had to do this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>moose@pc07:/usr/bin$ rm latex moose@pc07:/usr/bin$ sudo ln -s /usr/local/texlive/2013/bin/i386-linux/pdflatex latex </pre></div> </div> </div> <p>You can try if your installation works by <code>latex --version</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pdfTeX 3.1415926-1.40.10-2.2 (TeX Live 2009/Debian) kpathsea version 5.0.0 Copyright 2009 Peter Breitenlohner (eTeX)/Han The Thanh (pdfTeX). There is NO warranty. Redistribution of this software is covered by the terms of both the pdfTeX copyright and the Lesser GNU General Public License. For more information about these matters, see the file named COPYING and the pdfTeX source. Primary author of pdfTeX: Peter Breitenlohner (eTeX)/Han The Thanh (pdfTeX). Compiled with libpng 1.2.42; using libpng 1.2.42 Compiled with zlib 1.2.3.3; using zlib 1.2.3.3 Compiled with poppler version 0.12.4 </pre></div> </div> </div> <p>If an old version is shown, you might want to see where it is located:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>which latex </pre></div> </div> </div> <h2 id="update">Update</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>cd /usr/local/texlive/2013/bin/i386-linux sudo ./tlmgr update --self sudo ./tlmgr update --all </pre></div> </div> </div> <h2 id="see-also">See also</h2> <ul> <li>Wikipedia: <a href="http://en.wikipedia.org/wiki/LaTeX">LaTeX</a>, <a href="http://en.wikipedia.org/wiki/TeX_Live">TeX Live</a></li> <li>Wikibooks: <a href="http://en.wikibooks.org/wiki/LaTeX">LaTeX</a>, <a href="http://de.wikibooks.org/wiki/LaTeX-Kompendium">LaTeX-Kompendium</a> (German)</li> <li>UbuntuUsers (German): <a href="http://wiki.ubuntuusers.de/LaTeX">LaTeX</a></li> </ul> Incredible Optical Illusions //martin-thoma.com/incredible-optical-illusions/ Tue, 27 Mar 2012 12:05:01 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/incredible-optical-illusions <p>Some really great and short examples of illusions. If you want an explanation of them, I have added a link to the corresponding Wikipedia article.</p> <h2>Checker shadow illusion</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/checker-shadow-illusion-300x232.png"><img src="../images/2012/03/checker-shadow-illusion-300x232.png" alt="Checker shadow illusion" width="" height="" class="size-medium wp-image-20311" /></a><p class="wp-caption-text">Checker shadow illusion</p></div> <p><a href="http://en.wikipedia.org/wiki/Checker_shadow_illusion">Checker shadow illusion</a>: The pieces A and B are of the same color.</p> <h2>Ebbinghaus illusion</h2> <div style="width: 250px" class="wp-caption aligncenter"><a href="../images/2012/03/eigenhaus-illusion.png"><img src="../images/2012/03/eigenhaus-illusion.png" alt="Ebbinghaus illusion" width="" height="" class="size-full wp-image-20261" /></a><p class="wp-caption-text">Ebbinghaus illusion</p></div> <p><a href="http://en.wikipedia.org/wiki/Ebbinghaus_illusion">Ebbinghaus illusion</a>: the first central circle seems to be smaller than the second central circle although they are of identical size.</p> <p>The <a href="http://en.wikipedia.org/wiki/M%C3%BCller-Lyer_illusion">Müller-Lyer illusion</a> is simmilar.</p> <h2>Fraser spiral illusion</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/03/fraser-spiral-illusion.png"><img src="../images/2012/03/fraser-spiral-illusion.png" alt="Fraser spiral illusion" width="" height="" class="size-full wp-image-20201" /></a><p class="wp-caption-text">Fraser spiral illusion</p></div> <p>Although you think you see a spiral, there are only concentric circles. This illusion is knowen as <a href="http://en.wikipedia.org/wiki/Fraser_spiral_illusion">Fraser spiral illusion</a>.</p> <h2>Grid illiusion</h2> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2012/03/grid-illusion.png"><img src="../images/2012/03/grid-illusion.png" alt="Grid illusion" width="" height="" class="size-full wp-image-20221" /></a><p class="wp-caption-text">Grid illusion</p></div> <p>Dark dots seem to appear and disappear in the <a href="http://en.wikipedia.org/wiki/Grid_illusion">Grid illusion</a>.</p> <h2>Jastow illusion</h2> <div style="width: 343px" class="wp-caption aligncenter"><a href="../images/2012/03/jastow-illusion.png"><img src="../images/2012/03/jastow-illusion.png" alt="Jastrow illusion" width="" height="" class="size-full wp-image-20231" /></a><p class="wp-caption-text">Jastrow illusion</p></div> <p>In <a href="http://en.wikipedia.org/wiki/Jastrow_illusion">Jastow illusion</a>, the two figures are identical, although the lower one appears to be larger.</p> <h2>Z&ouml;llner illusion</h2> <div style="width: 235px" class="wp-caption aligncenter"><a href="../images/2012/03/zollner-illusion.png"><img src="../images/2012/03/zollner-illusion.png" alt="Z&ouml;llner illusion" width="" height="" class="size-full wp-image-20241" /></a><p class="wp-caption-text">Z&ouml;llner illusion</p></div> <p>In the figure of <a href="http://en.wikipedia.org/wiki/Z%C3%B6llner_illusion">Zöllner illusion</a> the black lines seem to be unparallel, but in reality they are parallel.</p> <h2>Hering illusion</h2> <div style="width: 135px" class="wp-caption aligncenter"><a href="../images/2012/03/hering-illusion.png"><img src="../images/2012/03/hering-illusion.png" alt="Hering illusion" width="" height="" class="size-full wp-image-20251" /></a><p class="wp-caption-text">Hering illusion</p></div> <p><a href="http://en.wikipedia.org/wiki/Hering_illusion">Hering illusion</a>: Two straight and parallel lines look as if they were bowed outwards.</p> <h2>Spinning Dancer</h2> <p>This image is the only animated one in this post.</p> <div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2012/03/spinning-dancer.gif"><img src="../images/2012/03/spinning-dancer.gif" alt="Spinning Dancer" width="" height="" class="size-full wp-image-20281" /></a><p class="wp-caption-text">Spinning Dancer</p></div> <p><a href="http://en.wikipedia.org/wiki/Spinning_Dancer">Spinning Dancer</a>: If the foot touching the ground is perceived to be the left foot, the dancer appears to be spinning clockwise (if seen from above); if it is taken to be the right foot, then she appears to be spinning counterclockwise.</p> <h2>Illusory motion</h2> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/03/motion-illusion.png"><img src="../images/2012/03/motion-illusion.png" alt="Illusory motion" width="" height="" class="size-full wp-image-20291" /></a><p class="wp-caption-text">Illusory motion</p></div> <p><a href="http://en.wikipedia.org/wiki/Illusory_motion">Illusory motion</a>: This image is not animated!</p> <h2>Caf&eacute; wall illusion</h2> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2012/03/cafe-wall-illusion.png"><img src="../images/2012/03/cafe-wall-illusion.png" alt="Caf&eacute; wall illusion" width="" height="" class="size-full wp-image-20351" /></a><p class="wp-caption-text">Caf&eacute; wall illusion</p></div> <p><a href="http://en.wikipedia.org/wiki/Caf%C3%A9_wall_illusion">Café wall illusion</a>: the parallel straight dividing lines between staggered rows with alternating black and white “bricks” appear to be sloped</p> Learn how to type //martin-thoma.com/learn-how-to-type/ Mon, 26 Mar 2012 17:40:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/learn-how-to-type <div style="width: 486px" class="wp-caption aligncenter"><a href="../images/2012/03/keybr.png"><img src="//martin-thoma.com/captions/keybr-2.png" alt="keybr - learn how to type" width="475" height="246" class=" wp-image-19691 " /></a><p class="wp-caption-text">keybr</p></div> <p><a href="http://keybr.com/">keybr.com</a> is another service that helps you to learn how to type.</p> Eigenschaften von Abbildungsmatrizen //martin-thoma.com/eigenschaften-von-abbildungsmatrizen/ Mon, 26 Mar 2012 17:30:44 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/eigenschaften-von-abbildungsmatrizen <p>Eine Abbildungsmatrix beschreibt eine lineare Abbildungs zwischen zwei endlichdimensionalen Vektorräumen. Sie ist abhängig von der Basis des Urraums und des Zielraumes.</p> <h2>Formale Definition</h2> <div class="definition">Eine <strong>Lineare Abbildung</strong> `$\Phi$` muss folgende Eigenschaften erf&uuml;llen: <ul> <li>`$\Phi: V \rightarrow W$` ist eine Abbildung</li> <li>`$\forall x, y \in W : \Phi(x+y) = \Phi(x) + \Phi(y)$`</li> <li>`$\forall x \in W : \forall a \in \mathbb{K}: \Phi(a \cdot x) = a \cdot \Phi(x)$`</li> </ul> </div> <p>Sei V ein n-dimensionaler <code>$\mathbb{K}$</code>-Vektorraum mit der Basis <code>$B = \{b_1, b_2, ..., b_n\}$</code> und W ein m-dimensonaler <code>$\mathbb{K}$</code>-Vektorraum mit der Basis <code>$C = \{c_1, c_2, ..., c_m\}$</code>.</p> <div class="definition"> Sei `$\Phi:V \rightarrow W$` eine lineare Abbildung. Dann ordnen wir der linearen Abbildung `$\Phi$` in folgender Weise eine Matrix A zu: `$\Phi (b_k) = \sum_{i=1}^{m} a_{ik}c_i, ~~ k = 1, ..., n, ~~ a_{ik}\in \mathbb{K}$` Dann gilt: `$\Phi(x) = A \cdot x ~~~\text{ mit } x \in V$` Diese Matrix A nennt man <strong>Abbildungsmatrix</strong>. </div> <h2>Beispiele</h2> <p>Sei <code>$\Phi: \mathbb{R}^4 \rightarrow \mathbb{R}^3$</code>.</p> <h3>Nullzeile</h3> <p><code>$A_1 = \left . \underbrace{\begin{pmatrix} 0 &amp;amp; 0 &amp;amp; 0 &amp;amp; 0 \\1 &amp;amp; 2 &amp;amp; 3 &amp;amp; 4 \\5 &amp;amp; 6 &amp;amp; 7 &amp;amp; 8 \end{pmatrix}}_\text{dim V} \right \} \text{dim W}$</code></p> <h4>Standardbasis</h4> <p>Sei <code>$B_S = (\begin{pmatrix} 1 \\ 0 \\ 0 \\ 0 \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 0 \\ 0 \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 1 \\ 0 \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 0 \\ 1 \end{pmatrix})$</code> und <code>$C_S = (\begin{pmatrix} 1 \\ 0 \\ 0 \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 0 \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 1 \end{pmatrix})$</code> Also sind B und C die geordnete Standardbasis des <code>$\mathbb{R}^4$</code> bzw. des <code>$\mathbb{R}^3$</code>.</p> <p>Was macht nun eine Abbildung <code>$\Phi$</code> mit der Matrix <code>$A_1$</code>?</p> <p>Ich denke ist ist leicht ersichtlich, dass bei einer Abbildungsmatrix dieser Form die erste Komponente des Bildvektors immer 0 ist.</p> <p><code>$\Phi_1(\begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix}) = \begin{pmatrix} 0 \\ 30 \\ 70 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=%7B%7B0%2C0%2C0%2C0%7D%2C%7B1%2C2%2C3%2C4%7D%2C%7B5%2C6%2C7%2C8%7D%7D.%7B%7B1%7D%2C%7B2%7D%2C%7B3%7D%2C%7B4%7D%7D">Wolfram|Alpha</a>) <code>$\Phi_1(\begin{pmatrix} 5 \\ -2 \\ 7 \\ -1 \end{pmatrix}) = \begin{pmatrix} 0 \\ 18 \\ 54 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=%7B%7B0%2C0%2C0%2C0%7D%2C%7B1%2C2%2C3%2C4%7D%2C%7B5%2C6%2C7%2C8%7D%7D.%7B%7B5%7D%2C%7B-2%7D%2C%7B7%7D%2C%7B-1%7D%7D">Wolfram|Alpha</a>)</p> <h4>Andere Basis</h4> <p>Sei <code>$B_1 = (\begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix}, \begin{pmatrix} 1 \\ 3 \\ 3 \\ 7 \end{pmatrix}, \begin{pmatrix} 3 \\ 1 \\ 4 \\ 1 \end{pmatrix}, \begin{pmatrix} 2 \\ 7 \\ 1 \\ 8 \end{pmatrix})$</code> und <code>$C_1 = (\begin{pmatrix} 2 \\ 3 \\ 5 \end{pmatrix}, \begin{pmatrix} 3 \\ 5 \\ 7 \end{pmatrix}, \begin{pmatrix} 5 \\ 7 \\ 11 \end{pmatrix})$</code></p> <p>Auch hier schauen wir uns wieder die Abbildung <code>$\Phi$</code> mit der Abbildungsmatrix <code>$A_1$</code> an.</p> <p><code>$\Phi_1(\underbrace{\begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix}}_\text{in Basis C}) = A_1 \cdot \begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix} = \underbrace{\begin{pmatrix} 0 \\ 30 \\ 70 \end{pmatrix}}_\text{in Basis B}$</code></p> <p>Auch hier ist also die erste Komponente jedes Bildvektors 0. Allerdings haben die Bildvektoren nun eine andere Basis. Sie werden sozusagen anders interpretiert.</p> <h3>Nullspalte</h3> <p><code>$A_2 = \begin{pmatrix} 0 &amp;amp; 1 &amp;amp; 2 &amp;amp; 3 \\0 &amp;amp; 4 &amp;amp; 5 &amp;amp; 6 \\0 &amp;amp; 7 &amp;amp; 8 &amp;amp; 9 \end{pmatrix}$</code></p> <p>Nun mal wieder zwei Beispiel-Abbildungen: <code>$\Phi_2(\begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix}) = \begin{pmatrix} 20 \\ 47 \\ 74 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=%7B%7B0%2C1%2C2%2C3%7D%2C%7B0%2C4%2C5%2C6%7D%2C%7B0%2C7%2C8%2C9%7D%7D.%7B%7B1%7D%2C%7B2%7D%2C%7B3%7D%2C%7B4%7D%7D">Wolfram|Alpha</a>) <code>$\Phi_2(\begin{pmatrix} 100 \\ 2 \\ 3 \\ 7 \end{pmatrix}) = \begin{pmatrix} 20 \\ 47 \\ 74 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=%7B%7B0%2C1%2C2%2C3%7D%2C%7B0%2C4%2C5%2C6%7D%2C%7B0%2C7%2C8%2C9%7D%7D.%7B%7B100%7D%2C%7B2%7D%2C%7B3%7D%2C%7B4%7D%7D">Wolfram|Alpha</a>)</p> <p>Wenn die Abbildungsmatrix eine Nullspalte hat, ist es egal was der abzubildende Vektor als Eintrag an dieser Stelle hat.</p> <h2>Basiswechsel bei Abbildungen</h2> <p>Ich habe ja gerade veranschaulicht, dass bei einem Basiswechsel zwar die Abbildung gleich bleibt, es aber dennoch unterschiedliche Vektoren sind. Sie müssen halt unterschiedlich interpretiert werden.</p> <p>Nun könnte man die Abbildung, also insbesondere die Matrix, so ändern, dass die Vektoren, die man als “gleich” interpretieren würde, gleich abgebildet werden.</p> <p>Wir suchen also eine neue Abbildungsmatrix <code>$A_1'$</code>, die die gleiche Abbildung beschreibt wie <code>$A_1$</code> mit den Standardbasen, nur von <code>$B_1$</code> nach <code>$C_1$</code>.</p> <p>Wenn man das machen will, kann man sich den Vorgang wie eine Ansammlung von Funktionen (im Sinne der Informatik) betrachten. Wir haben eine Funktion, die die Abbildung von der Standardbasis in die Standardbasis beschreibt. Als Input bekommen wir einen Vektor in der Basis <code>$B_1$</code> und herauskommen soll ein Vektor in der Basis <code>$C_1$</code>. Wir müssen also den Input-Vektor von der Basis <code>$B_1$</code> in die Standardbasis umwandeln und den Output-Vektor der gegebenen Funktion von der Standardbasis in die Basis <code>$C_1$</code> konvertieren.</p> <p>Dazu bestimmen wir zuerst die Basiswechselmatrix <code>$T_S^{B1}$</code> von der Basis <code>$B_1$</code> in die Standardbasis. Das ist genau die Basis selbst: ` <script type="math/tex">% <![CDATA[ T_{B1}^S = \begin{pmatrix} 1 & 1 & 3 & 2 \\ 2 & 3 & 1 & 7 \\ 3 & 3 & 4 & 1 \\ 4 & 7 & 1 & 8 \end{pmatrix} %]]></script>` (siehe alten <a title="Wie bestimme ich die Basiswechselmatrix?" href="../wie-bestimme-ich-die-basiswechselmatrix/">Blogpost</a>)</p> <p>Und die Basiswechselmatrix <code>$T_S^{C1}$</code> von der Standardbasis in die Basis <code>$C_1$</code>. Das ist das Inverse der Basis <code>$C_1$</code>:</p> <p><code> $$ T_S^{C1} = \frac{1}{2} \cdot \begin{pmatrix} -6 &amp; -2 &amp; 4 \\ -2 &amp; 3 &amp; -1 \\ 4 &amp; -1 &amp; -1 \end{pmatrix} $$</code></p> <p>Insgesamt sieht das dann so aus: <code>$T_S^{C1} \cdot (A_1 \cdot (T_{B1} \cdot x))$</code>. Da für die Matrixmultiplikation das <a href="http://de.wikipedia.org/wiki/Assoziativgesetz">Assoziativgesetz</a> gilt, kann man das vereinfachen:</p> <p><code> $$ A_1′ = T_S^{C1} \cdot A_1 \cdot T_{B1}^S = \begin{pmatrix} 110 &amp; 156 &amp; 93 &amp; 195 \\ 10 &amp; 16 &amp; 3 &amp; 15 \\ -50 &amp; -72 &amp; -39 &amp; -87 \end{pmatrix} $$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=%7B%7B-3%2C+-1%2C+2%7D%2C+%7B-1%2C+3%2F2%2C+-1%2F2%7D%2C+%7B2%2C+-1%2F2%2C+-1%2F2%7D%7D+*+%7B%7B0%2C0%2C0%2C0%7D%2C%7B1%2C2%2C3%2C4%7D%2C%7B5%2C6%2C7%2C8%7D%7D+*+%7B%7B1%2C1%2C3%2C2%7D%2C%7B2%2C3%2C1%2C7%7D%2C%7B3%2C3%2C4%2C1%7D%2C%7B4%2C7%2C1%2C8%7D%7D">Wolfram|Alpha</a>)</p> <p>Ein Test ob es stimmen kann: z.B. sind <code>$\begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix}_S = 1 \cdot \begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix} + 0 \cdot \begin{pmatrix} 1 \\ 3 \\ 3 \\ 7 \end{pmatrix} + 0 \cdot \begin{pmatrix} 3 \\ 1 \\ 4 \\ 1 \end{pmatrix} + 0 \cdot \begin{pmatrix} 2 \\ 7 \\ 1 \\ 8 \end{pmatrix} = \begin{pmatrix} 1 \\ 0 \\ 0 \\ 0 \end{pmatrix}_{B_1} $</code> und <code>$\begin{pmatrix} 0 \\ 30 \\ 70 \end{pmatrix}_S = 110 \cdot \begin{pmatrix} 2 \\ 3 \\ 5 \end{pmatrix} + 10 \cdot \begin{pmatrix} 3 \\ 5 \\ 7 \end{pmatrix} -50 \cdot \begin{pmatrix} 5 \\ 7 \\ 11 \end{pmatrix} = \begin{pmatrix} 110 \\ 10 \\ -50 \end{pmatrix}_{C_1}$</code></p> <p><code>$\begin{pmatrix} 110 &amp;amp; 156 &amp;amp; 93 &amp;amp; 195 \\ 10 &amp;amp; 16 &amp;amp; 3 &amp;amp; 15 \\ -50 &amp;amp; -72 &amp;amp; -39 &amp;amp; -87 \end{pmatrix} \cdot \begin{pmatrix} 1 \\ 0 \\ 0 \\ 0 \end{pmatrix}_{B_1} = \begin{pmatrix} 110 \\ 10 \\ -50 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=%7B%7B110%2C+156%2C+93%2C+195%7D%2C+%7B10%2C+16%2C+3%2C+15%7D%2C+%7B-50%2C+-72%2C+-39%2C+-87%7D%7D+*+%7B%7B1%7D%2C%7B0%7D%2C%7B0%7D%2C%7B0%7D%7D">Wolfram|Alpha</a>)</p> <p>Ich habe keine Ahnung, wie man nur mit den Basen B und C und der Abbildungsmatrix <code>$A_1'$</code> wieder auf die Abbildungsmatrix <code>$A_1$</code> kommt. Ich habe auf <a title="How can I determinate the bases for the most simple representation of a linear transformation?" href="http://math.stackexchange.com/q/123495/6876">Stackexchange</a> mal nachgefragt, aber das ist nicht von Erfolg gekrönt gewesen.</p> <h2>Anzahl der Abbildungsmatrizen</h2> <p>Für jede lineare Abbildungen <code>$\Phi: V \rightarrow W$</code> (wobei V und W <strong>endliche</strong> Vektorräume sind) gibt es eine Abbildungsmatrix.</p> <p>Wie sieht dann die Abbildungsmatrix folgender Abbildung aus?</p> <blockquote>Sei `$V:= \{p \in \mathbb{R}[t] | deg(t) \leq 5 \}$` der Vektorraum aller Polynome in t mit reellen Koeffizienten und Grad `$ \leq 5$`. Sei `$F: V \rightarrow V$` die Shift-Abbildung `$(Fp)(t) = p(t+1)$` <p class="quote-source">(Quelle: <a href="http://matheraum.de/forum/Shift-Abbildung/t463098">Matheraum.de</a>)</p> </blockquote> <p>Wenn V allerdings der <code>$\mathbb{Z}/ 2 \mathbb{Z}$</code> und W der <code>$\mathbb{Z}/ 3 \mathbb{Z}$</code> über jeweils den Körper <code>$\mathbb{Z}/ 2 \mathbb{Z}$</code> sind, dann ist die Abbildungsmatrix eine 1x1 Matrix. Das eine Element dieser 1x1 Matrix kann zwei verschiedene Werte - 0 und 1 - annehmen. Selbst wenn W der <code>$\mathbb{Z}/ 41 \mathbb{Z}$</code> wäre, würde es nur zwei verschiedene Abbildungen geben.</p> <p>Wenn V der <code>$\mathbb{Z}/ 3 \mathbb{Z}$</code> und W der <code>$\mathbb{Z}/ 2 \mathbb{Z}$</code> ist, dann gibt es nur eine lineare Abbildung <code>$\Phi: V \rightarrow W$</code>(die Nullabbildung). Die Abbildungsmatrix <code>$\begin{pmatrix}1\end{pmatrix}$</code> bezeichnet keine lineare Abbildung <code>$\Phi$</code>, da 2 in V ist, aber nicht in W.</p> <p>Es scheint also so zu sein, dass man im Allgemeinen nichts über die Anzahl der linearen Abbildungen sagen kann.</p> <h2>Dies und das</h2> <p>Zwei lineare Abbildungen können hintereinander ausgeführt werden, indem ihre Matrizen multipliziert werden: <code>$\Phi_1 : V \rightarrow W, \Phi_1(x) := A_1 \cdot x$</code> <code>$\Phi_2 : W \rightarrow X, \Phi_2(x) := A_2 \cdot x$</code> <code>$\Phi_2 \circ \Phi_1 : V \rightarrow X, x \mapsto \Phi_2 \circ \Phi_1(x) := \Phi_2(\Phi_1(x)) = A_2 \cdot (A_1 \cdot x) = (A_2 \cdot A_1) \cdot x$</code></p> <p>Der Rang der Abbildungsmatrix entspricht der Dimension des Bildes der Abbildung.</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Vektorraum">Vektorraum</a>, <a href="http://de.wikipedia.org/wiki/Abbildungsmatrix">Abbildungsmatrix</a>, <a href="http://de.wikipedia.org/wiki/Rang_(Mathematik)">Rang</a></li> <li><a title="Wie bestimme ich die Basiswechselmatrix?" href="../wie-bestimme-ich-die-basiswechselmatrix/">Wie bestimme ich die Basiswechselmatrix?</a></li> <li>Skript von Prof. Dr. Leunzinger, ab S. 101 (im passwortgesch&uuml;tzten <a href="https://studium.kit.edu/sites/vab/0x869D2B3648EA0D498D68FE4A6098E555/Vorlesungsunterlagen/Forms/AllItems.aspx">VAB</a>)</li> </ul> Wie bestimme ich das Inverse einer Matrix? //martin-thoma.com/wie-bestimme-ich-das-inverse-einer-matrix/ Tue, 20 Mar 2012 16:07:50 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-bestimme-ich-das-inverse-einer-matrix <p>Nicht alle Matrizen sind invertierbar. Matrizen, die invertierbar sind, nennt man auch regulär. Die Menge aller invertierbaren <code>$n \times n$</code>–Matrizen über einem Grundkörper (oder Grundring) K bildet eine Gruppe bezüglich der Matrixmultiplikation, die allgemeine lineare Gruppe <code>$GL_n(K)$</code>.</p> <table> <tbody> <tr> <td>Das Inverse einer Matrix A wird berechnet, indem eine Matrix (A</td> <td>E) gebildet wird und mit dem Gaußschem Eliminationsverfahren in <code>$(E | A^{-1})$</code> aufgelöst wird.</td> </tr> </tbody> </table> <h2>Beispiel</h2> <h3>Ein Inverses existiert</h3> <p><code>$\left( \begin{array}{c c c c | c c c c} 4 &amp; 2 &amp; 4 &amp; 2 &amp; 1 &amp; 0 &amp; 0 &amp; 0 \\ 3 &amp; 1 &amp; 4 &amp; 1 &amp; 0 &amp; 1 &amp; 0 &amp; 0\\ 2 &amp; 7 &amp; 1 &amp; 8 &amp; 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 1 &amp; 1 &amp; 2 &amp; 0 &amp; 0 &amp; 0 &amp; 1 \end{array} \right) \rightsquigarrow \left( \begin{array}{c c c c | c c c c} 2 &amp; 1 &amp; 2 &amp; 1 &amp; \frac{1}{2} &amp; 0 &amp; 0 &amp; 0 \\ 0 &amp; -\frac{1}{2} &amp; 1 &amp; -\frac{1}{2} &amp; -\frac{3}{4} &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 6 &amp; -1 &amp; 7 &amp; -\frac{1}{2} &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 1 &amp; 1 &amp; 2 &amp; 0 &amp; 0 &amp; 0 &amp; 1 \end{array} \right)$</code></p> <p><code>$\rightsquigarrow^* \frac{1}{8} \begin{pmatrix} 12 &amp; -12 &amp; -2 &amp; 2 \\ -16 &amp; 18 &amp; 5 &amp; -13 \\ -8 &amp; 10 &amp; 1 &amp; -1 \\ 12 &amp; -14 &amp; -3 &amp; 11 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=Inverse%5B%7B%7B4%2C2%2C4%2C2%7D%2C%7B3%2C1%2C4%2C1%7D%2C%7B2%2C7%2C1%2C8%7D%2C%7B0%2C1%2C1%2C2%7D%7D%5D">Wolfram|Alpha</a>)</p> <h3>Kein Inverses existiert</h3> <p>Matrizen, zu denen kein Inverses existiert, werden singulär genannt. Das ist ein Beispiel: <code>$\begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 0 \\ 0 &amp; 1 &amp; 0 &amp; 0 \\ 0 &amp; 0 &amp; 1 &amp; 0 \\ 0 &amp; 0 &amp; 1 &amp; 0 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=Inverse%5B%7B%7B1%2C0%2C0%2C0%7D%2C%7B0%2C1%2C0%2C0%7D%2C%7B0%2C0%2C1%2C0%7D%2C%7B0%2C0%2C1%2C0%7D%7D%5D">Wolfram|Alpha</a>) Sobald also erkennbar ist, dass beim Eliminationsverfahren eine Nullzeile auftritt, kann man abbrechen.</p> <p>Matrizen, die nicht quadratisch sind, haben kein Inverses: <code>$\begin{pmatrix} 1 &amp; 0 &amp; 0 \\ 0 &amp; 1 &amp; 0 \\ 0 &amp; 0 &amp; 1 \\ 0 &amp; 0 &amp; 2 \end{pmatrix}$</code> (siehe <a href="http://www.wolframalpha.com/input/?i=Inverse%5B%7B%7B1%2C0%2C0%7D%2C%7B0%2C1%2C0%7D%2C%7B0%2C0%2C1%7D%2C%7B0%2C0%2C2%7D%7D%5D">Wolfram|Alpha</a>)</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Regul%C3%A4re_Matrix">Regul&auml;re Matrix</a>, <a href="http://de.wikipedia.org/wiki/Gau%C3%9Fsches_Eliminationsverfahren">Gau&szlig;sches Eliminationsverfahren</a></li> <li>Skript von Prof. Dr. Leuzinger, ab S. 53</li> </ul> Wie bestimme ich die Basiswechselmatrix? //martin-thoma.com/wie-bestimme-ich-die-basiswechselmatrix/ Fri, 16 Mar 2012 17:06:11 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-bestimme-ich-die-basiswechselmatrix <p>Eine Basiswechselmatrix oder auch Übergangsmatrix dient dem Basiswechsel.</p> <p>Angenommen man hat zwei Basen des <code>$\mathbb{R}^2$</code>-Vektorraumes:</p> <p>[B = {\overbrace{\begin{pmatrix} 1 \ 2 \end{pmatrix}}^{b_1}, \overbrace{\begin{pmatrix} 2 \ 3 \end{pmatrix}}^{b_2} }]</p> <p>und</p> <p>[\bar B = {\underbrace{\begin{pmatrix} 3 \ 5 \end{pmatrix}}<em>{\bar b_1}, \underbrace{\begin{pmatrix} 8 \ 13 \end{pmatrix}}</em>{\bar b_2} }]</p> <p>Sei nun <code>$v := \begin{pmatrix} 1 \\ 1 \end{pmatrix}$</code> ein Vektor zur Standardbasis. Da <code>$B$</code> und <code>$\bar B$</code> auch Basen des <code>$\mathbb{R}^2$</code> sind, kann man v auch zu diesen Basen darstellen: <code>$\Theta_{B}(v) = \begin{pmatrix} -1 \\ 1 \end{pmatrix}$</code> und <code>$\Theta_{\bar B}(v) = \begin{pmatrix} -5 \\ 2 \end{pmatrix}$</code></p> <p>Wie kann man nun diese neue Darstellung berechnen? Nun, wir bestimmen eine Matrix A für die gilt: <code>$A \cdot \Theta_B(v) = \Theta_{\bar B}(v) ~~~ \forall v \in \mathbb{R}^2$</code>. Diese Matrix findet man, indem man beide geordneten Basen nebeneinander schreibt und die rechte Seite “durchgaußt”: <code>$\left( \begin{array}{c c | c c} 1 &amp; 2 &amp; 3 &amp; 8 \\ 2 &amp; 3 &amp; 5 &amp; 13 \end{array} \right) \rightsquigarrow \left( \begin{array}{c c | c c} \frac{1}{3} &amp; \frac{2}{3} &amp; 1 &amp; \frac{8}{3} \\ 2 &amp; 3 &amp; 5 &amp; 13 \end{array} \right) \rightsquigarrow \\ \left( \begin{array}{c c | c c} \frac{1}{3} &amp; \frac{2}{3} &amp; 1 &amp; \frac{8}{3} \\ \frac{6-5}{3} &amp; \frac{9-10}{3} &amp; 0 &amp; \frac{39-8 \cdot 5}{3} \end{array} \right) \rightsquigarrow \left( \begin{array}{c c | c c} \frac{1}{3} &amp; \frac{2}{3} &amp; 1 &amp; \frac{8}{3} \\ \frac{1}{3} &amp; -\frac{1}{3} &amp; 0 &amp; -\frac{1}{3} \end{array} \right) \rightsquigarrow \\ \left( \begin{array}{c c | c c} \frac{9}{3} &amp; -\frac{6}{3} &amp; 1 &amp; 0 \\ \frac{1}{3} &amp; -\frac{1}{3} &amp; 0 &amp; -\frac{1}{3} \end{array} \right) \rightsquigarrow \left( \begin{array}{c c | c c} 3 &amp; -2 &amp; 1 &amp; 0 \\ -1 &amp; 1 &amp; 0 &amp; 1 \end{array} \right)$</code></p> <table> <tbody> <tr> <td>Links steht die geordnete Basis B und rechts die geordnete Basis <code>$\bar B$</code>, also (von</td> <td>nach) und rechts wendet man Gauß an.</td> </tr> </tbody> </table> <p>Nun noch die Kontrolle, ob es stimmen kann: [\underbrace{\begin{pmatrix} 3 &amp; -2 \ -1 &amp; 1 \end{pmatrix}}<em>{A</em>{B \bar B}} \cdot \underbrace{\begin{pmatrix} -1 \ 1 \end{pmatrix}}<em>{\Theta</em>{B}(v)} = \underbrace{\begin{pmatrix} -5 \ 2 \end{pmatrix}}<em>{\Theta</em>{\bar B}(v)}]</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Basiswechsel_(Vektorraum)">Basiswechsel (Vektorraum)</a>, <a href="http://de.wikipedia.org/wiki/Standardbasis">Standardbasis</a></li> <li>Skript von Prof. Dr. Leuzinger, ab S. 82</li> </ul> Typography: Word as Image //martin-thoma.com/typography-word-as-image/ Mon, 12 Mar 2012 14:06:34 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/typography-word-as-image <iframe width="512" height="290" src="http://www.youtube.com/embed/J59n8FsoRLE" frameborder="0" allowfullscreen=""></iframe> <p>Challenge: Create an image out of a word, using only the letters in the word itself.</p> <p>Rule: Use only the graphic elements of the letters without adding outside parts.</p> Computer Science Jokes //martin-thoma.com/computer-science-jokes/ Sun, 11 Mar 2012 00:04:54 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/computer-science-jokes <div class="info">You have to read <a href="http://stackoverflow.com/q/234075/562769">What is your best programmer joke?</a>, <a href="http://stackoverflow.com/q/218123/562769">What was the strangest coding standard rule that you were forced to follow?</a> and <a href="http://stackoverflow.com/q/184618/562769">What is the best comment in source code you have ever encountered?</a></div> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/03/hello-world-cartoon.jpg"><img src="//martin-thoma.com/captions/hello-world-cartoon.jpg" alt="Hello World Cartoon" width="512" height="487" class=" wp-image-18071 " /></a><p class="wp-caption-text">Hello World Cartoon</p></div> <p>Programming is like sex: One mistake and you have to support it for the rest of your life.</p> <div style="width: 494px" class="wp-caption aligncenter"><a href="../images/2012/03/write-500-words-count-cpp.jpg"><img src="../images/2012/03/write-500-words-count-cpp.jpg" alt="Write 500 words on board with C++" width="" height="" class="size-full wp-image-18111" /></a><p class="wp-caption-text">Write 500 words on board with C++</p></div> <p>What’s the difference between drug dealers and computer programmers?</p> <table> <tr> <th>Drug Dealers</th> <th>Computer Programmers</th> </tr> <tr> <td>Refer to their clients as &ldquo;users&rdquo;.</td> <td>Refer to their clients as &ldquo;users&rdquo;.</td> </tr> <tr> <td>&ldquo;The first one&rsquo;s free!&rdquo;</td> <td>&ldquo;Download a free trial version&hellip;&rdquo;</td> </tr> <tr> <td>Have important South-East Asian connections (to help move the stuff).</td> <td>Have important South-East Asian connections (to help debug the code).</td> </tr> <tr> <td>Strange jargon: &ldquo;Stick,&rdquo; &ldquo;Rock,&rdquo; &ldquo;Dime bag,&rdquo; &ldquo;E&rdquo;.</td> <td>Strange jargon: &ldquo;SCSI,&rdquo; &ldquo;RTFM,&rdquo; &ldquo;Java,&rdquo; &ldquo;ISDN&rdquo;.</td> </tr> <tr> <td>Realize that there&rsquo;s tons of cash in the 14- to 25-year-old market.</td> <td>Realize that there&rsquo;s tons of cash in the 14- to 25-year-old market.</td> </tr> <tr> <td>Job is assisted by the industry&rsquo;s producing newer, more potent mixes.</td> <td>Job is assisted by industry&rsquo;s producing newer, faster machines.</td> </tr> <tr> <td>Often seen in the company of pimps and hustlers.</td> <td>Often seen in the company of marketing people and venture capitalists.</td> </tr> <tr> <td>Their product causes unhealthy addictions.</td> <td>DOOM. Quake. FarmVille. CS. &lsquo;Nuff said.</td> </tr> <tr> <td>Do your job well, and you can sleep with sexy movie stars who depend on you.</td> <td>Damn! Damn! DAMN!!!</td> </tr> </table> <figure class="wp-caption aligncenter"> <img src="http://imgs.xkcd.com/comics/compiling.png" alt="xkcd: Compiling" /> <figcaption>xkcd: Compiling</figcaption> </figure> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>ME: You should really think about a new monitor. CLIENT: I would, but I don&amp;rsquo;t want to lose my icons. </pre></div> </div> </div> <p>(Source: Clients From Hell)</p> <div style="width: 292px" class="wp-caption aligncenter"><a href="../images/2012/03/computer-science-major-282x300.png"><img src="../images/2012/03/computer-science-major-282x300.png" alt="Computer Science Major - possibly from abstrusegoose" width="" height="" class="size-medium" /></a><p class="wp-caption-text">Computer Science Major - possibly from &lt;a href=http://abstrusegoose.com/a/206.htm&gt;abstrusegoose</p></div> <p>There are 10 types of people: those who understand binary, and those who do not understand it.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/why-people-seem-to-have-freetime-300x248.png"><img src="../images/2012/03/why-people-seem-to-have-freetime-300x248.png" alt="Why people seem to have freetime" width="" height="" class="size-medium" /></a><p class="wp-caption-text">Why people seem to have freetime</p></div> <h2>More Jokes!</h2> <ul> <li><a href="http://bash.org/?random">Bash.org</a></li> <li><a href="http://bofh.ch/">Bastard Operator from Hell</a></li> <li><a href="http://clientsfromhell.net/">Clients From Hell</a></li> <li><a href="http://www.cs.cmu.edu/~eugene/quotes/prog.html">cs.cmu.edu</a></li> </ul> Abschlussaufgaben Programmieren //martin-thoma.com/abschlussaufgaben-programmieren/ Sat, 10 Mar 2012 16:00:13 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/abschlussaufgaben-programmieren <p><strong>Hinweis</strong>: Dieser Blogpost ist vermutlich nur für Informatik-Studenten am KIT im WS 2011 / 2012 interessant!</p> <p>Hier ein paar Hinweise zu den Abschlussaufgaben aus dem Forum. Dabei habe ich die Antworten von jgraf, mmohr und praktomat genommen.</p> <h2>Allgemeines</h2> <ul> <li>Was wir absolut nicht sehen wollen sind grosse Methoden, die verstreut &uuml;ber den ganzen Code diverse returns enth&auml;lt. Eventuell sollte man diese Methode dann ohnehin in Hilfsmethoden aufteilen.</li> <li>Parameter: Die Anzahl der Parameter muss exakt stimmen. Sind zu &uuml;berz&auml;hlige Parameter vorhanden, muss ein Fehler ausgegeben werden.</li> <li>toString/equals: Sollte nur f&uuml;r Klassen geschrieben werden, bei denen es Sinn macht. Vor allem auf eins aufpassen: Wenn man equals &uuml;berschreibt, dann sollte man auch hashCode &uuml;berschreiben (siehe <a href="http://docs.oracle.com/javase/1.4.2/docs/api/java/lang/Object.html#equals(java.lang.Object">docs.oracle.com</a>) bzw, beliebige suche nach "equals hashCode"). Mir fallen spontan wenige F&auml;lle ein, wo es keinen Sinn macht, equals()/hashCode() oder toString() zu &uuml;berschreiben. Die Shell ist vielleicht so ein Fall, oder auch Utility-Klassen. </li> <li>Verbergt die tats&auml;chlichen Typen, woimmer es m&ouml;glich ist! Also z.B. <code>private Map meineMap = new HashMap&lt;Integer, Blub&gt;();</code></li> </ul> <blockquote>Frage: D&uuml;rfen Strings direkt im Programmcode stehen, oder sollten diese gesammelt am Beginn einer Klasse stehen?</blockquote> <p>Antwort: Kommt darauf an, wenn Sie mehr als eimal verwendet werden, dann sollte man Konstanten daraus machen.</p> <blockquote>Frage: Soll die Shell nur korrekte Werte an den eigentlichen LittlePraktomat &uuml;bergeben, also alle Fehlerquellen bereits in der Shell-Klasse abgefangen werden oder soll der LittlePraktomat Exceptions werfen, die in der Shell dann gefangen werden? Oder soll beides gemacht werden?</blockquote> <p>Antwort: Die öffentlichen Methoden einer Klasse sind deren Schnittstelle. In den Javadoc Kommentaren sollte stehen, wie diese Schnittstelle zu verwenden ist. Also welcher Art die Eingaben sein müssen und wie die Ausgaben aussehen. Wenn sich ein Aufrufer nicht and diese Vereinbarung hält, dann sollte die Methode der Schnittstelle eine Exception werfen (IllegalArgument, NullPointer, …). Diese Exceptions sollten normalerweise nie vom Aufrufer gefangen werden. Sie sollen das Program kontrolliert zum Absturz bringen. Die Logik dahinter ist folgende: Wenn eine IllegalArgumentException (oder ähnliches) fliegt, dann wurde eine Schnittstelle falsch verwendet. Der Aufrufer der Schnittstelle hat aber vor dem Aufruf sicher zu stellen, dass alle Forderungen der Schnittstelle eingehalten werden. D.h. wenn eine solche Exception auftritt liegt ein Programmierfehler vor. Mit Hilfe des Exceptionstacktrace kann der Entwickler diesen realtiv bequem finden und beheben.</p> <p>Es ist also beides zu machen, die Shell (der Aufrufer) hat vor dem Verwenden der Praktomat-Schnittstelle sicher zu stellen, dass alle Eingaben korrekt sind. Sind die Eingaben falsch, dann wird eine Fehlermeldung ausgegeben. Die Praktomat-Schnittstelle schützt sich vor falscher Verwendung mit Hilfe von Exceptions.</p> <h2>Tests</h2> <p>Ihr <strong>müsst</strong> eine Tests.txt mit abgeben. Die ist wie ein Beispiel aufgebaut und sollt wichtige Eingaben / Ausgaben enthalten, die eventuell zu Fehlern führen könnten.</p> <p>Da ihr sie ja sowieso schreibt, könnt ihr euer Programm auch auf eure Tests.txt überprüfen. Ich habe mir dazu folgendes kleines <a href="../images/2012/03/programmieren-abschlussaufgabe.zip">Python-Script zum Vergleichen</a> gebastelt und vergleiche dann den normalisierten realen Output mit hilfe von <a href="http://wiki.ubuntuusers.de/Meld">Meld</a> mit dem erwartetem Output.</p> <p>Also folgendes in der Bash:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python checkTests.py meld ../tmp/createdOutputNormalized.txt ../tmp/compareTo.txt</code></pre></div> <p>Ihr müsst halt noch die Pfade anpassen.</p> <h2>Abschlussaufgabe 1</h2> <p>Folgendes zum LittlePraktomat:</p> <ul> <li>Falls die Namen von Personen etwas anderes als Kleinbuchstaben haben (also z.B. Gro&szlig;buchstaben!) soll ein Fehler ausgegeben werden. &auml;&ouml;&uuml; m&uuml;ssen nicht als Kleinbuchstaben erkannt werden, a-z reicht.</li> </ul> <h2>Abschlussaufgabe 2</h2> <p>Folgendes zu <a href="http://de.wikipedia.org/wiki/Othello_(Spiel)">Othello</a>:</p> <ul> <li>Wer sehr schnell die Aufgabe erledigt hatte (also noch am ersten Tag), dem fehlen hier eventuell ein paar Sachen. Habt ihr den hole-Befehl? Falls ja, ist alles ok. Sonst solltet ihr nochmals rein schauen und eure L&ouml;sung nochmals hochladen, weil eine veraltete Aufgabenstellung zu beginn hochgeladen wurde.</li> <li>Eine g&uuml;ltige Spielfeldgr&ouml;&szlig;e MUSS gerade breite / h&ouml;he haben, gr&ouml;&szlig;er als 0x0 sein und kleiner gleich 26x98 sein.</li> <li>Ein g&uuml;ltiges Rechteck MUSS die erste Koordinate links oben und die zweite rechts unten haben!</li> </ul> <p>Es gibt folgende Befehle:</p> <ul> <li>newGame <breite> &lt;H&ouml;he&gt; [<stellung>] <li>hole <rechteck> <li>move <position> <li>print</li> <li>abort</li> <li>possibleMoves</li> <li>quit</li> <h2>Daten</h2> <strong>Abschlussaufgabe 1</strong>: 01.02.2012 - 12.03.2012 Funktionalit&auml;t: 0 - 7 Punkte Programmiermethodik: 0 - 7 Punkte Endnote = (2 &middot; Funktionalit&auml;t + Programmiermethodik) <strong>Abschlussaufgabe 2</strong>: 13.02.2012 - 26.03.2012, 13:00 Uhr Funktionalit&auml;t: 0 - 7 Punkte Programmiermethodik: 0 - 7 Punkte Endnote = (2 &middot; Funktionalit&auml;t + Programmiermethodik) <h2>Ergebnisse</h2> Mir wird, wenn ich im Abschlussaufgaben-Praktomat auf "Home" klicke, bereits angezeigt, dass es anscheinend maximal 24 Punkte auf die "Abschlu&szlig;aufgabe 1: Little Praktomat" gibt. Bin ja mal gespannt, wann es Ergebnisse gibt. Es gab jeweils auf Funktionalit&auml;t und Programmiermethodik 14 Punkte, wobei die Punktzahl der Funktionalit&auml;t verdoppelt wurde. Damit kommen wir insgesamt auf 2 * (14*2 + 14)= 84 Punkte. Der Notenschl&uuml;ssel ist wie folgt: <table> <tr><th>Bewertungspunkte</th><th>Gesamtnote</th></tr> <tr><td>82,0 - 84,0</td><td>1,0</td></tr> <tr><td>78,0 - 81,5</td><td>1,3</td></tr> <tr><td>74,0 - 77,5</td><td>1,7</td></tr> <tr><td>70,0 - 73,5</td><td>2,0</td></tr> <tr><td>66,0 - 69,5</td><td>2,3</td></tr> <tr><td>62,0 - 65,5</td><td>2,7</td></tr> <tr><td>58,0 - 61,5</td><td>3,0</td></tr> <tr><td>54,0 - 57,5</td><td>3,3</td></tr> <tr><td>50,0 - 53,5</td><td>3,7</td></tr> <tr><td>46,0 - 49,5</td><td>4,0</td></tr> <tr><td>0 - 45,5</td><td>5,0 - nicht bestanden</td></tr> </table> <h2>Meine Abgabe</h2> <ul> <li>LittlePraktomat: <a href="http://www.martin-thoma.de/programmieren-little-praktomat/class-diagram/class-diagram.pdf">Klassendiagramm</a> + <a href="http://www.martin-thoma.de/programmieren-little-praktomat/">JavaDoc</a> + <a href="../images/2012/03/little-praktomat.zip">Java Source Code</a></li> <li>Othello: <a href="http://www.martin-thoma.de/programmieren-othello/">JavaDoc</a> + <a href="../images/2012/03/othello.zip">Java Source Code</a></li> </ul> <h3>Fehlerquellen</h3> Es wurde bem&auml;ngelt, dass ich wenig Kommentare hab. Ich finde, ich habe wahnsinnig viele ... <h4>LittlePraktomat</h4> <strong>Test 4</strong>: Eingabe: list-solutions 99999999999999999999 Exception in thread "main" java.lang.NumberFormatException - die Zahl ist zu gro&szlig; <strong>Test 7</strong>: Aus Bl&ouml;dheit nicht bestanden ... ich habe eine Funktion (das wechseln von Tutoren) nicht &uuml;berpr&uuml;ft. <h4>Othello</h4> <strong>Test 6 b</strong>: Direkt nach dem Start des Programms "hole A1:A1" hat eine (meiner eigenen) Exceptions geworfen ... bzw. mit korrekter Angabe, wo der Fehler liegt ... also auch Dummheit *argh* </position></li></rechteck></li></stellung></breite></li></ul> How to fill holes in your wall / ceiling //martin-thoma.com/how-to-fill-holes-in-your-wall-ceiling/ Mon, 05 Mar 2012 22:08:41 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-fill-holes-in-your-wall-ceiling <div style="width: 138px" class="wp-caption alignright"><a href="../images/2011/10/do-it-yourself-thumb.jpg"><img src="../images/2011/10/do-it-yourself-thumb.jpg" alt="Do-it-yourself - Some random tools (Thumbnail)" width="" height="" class="size-full wp-image-4861 " /></a><p class="wp-caption-text">Do-it-yourself - Some random tools (Thumbnail)</p></div> <p>I’ve decided to fill some holes in my ceiling and my wall today. I don’t want to paint my room the next time as it is too cold at the moment, but the holes were really ugly. I’ve added a photo of them. So I went to the next hardware store and asked what could be done. I thought I needed to use gypsum which is grey, so it wouldn’t look very good. Additionally you can buy gypsum only in 1.5 kg bags. <br /> <br /> <br /></p> <h2>Situation before</h2> <div style="width: 624px" class="wp-caption aligncenter"><a href="../images/2012/03/loch-in-der-decke-1024x563.jpg"><img src="//martin-thoma.com/captions/loch-in-der-decke-1024x563.jpg" alt="Holes in the ceiling before I fixed it." width="614" height="338" class=" wp-image-17171 " /></a><p class="wp-caption-text">Holes in the ceiling</p></div> <h2>The tools</h2> <p>The guy at the hardware store suggested to use acrylic paint. So I did. These were the tools I needed:</p> <ul> <li><a href="http://en.wikipedia.org/wiki/Acrylic_paint">Acrylic paint</a>: about 4.00 Euro</li> <li>some <a href="http://en.wikipedia.org/wiki/Masking_tape">masking tape</a></li> <li>a <a href="http://en.wikipedia.org/wiki/Putty_knife">putty knife</a></li> </ul> <table> <tr> <td><div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2012/03/kreppband-japanspachtel-150x150.jpg"><img src="../images/2012/03/kreppband-japanspachtel-150x150.jpg" alt="Kreppband und Japanspachtel" width="" height="" class="size-thumbnail wp-image-17231" /></a><p class="wp-caption-text">Masking tape and putty knife</p></div></td> <td><div style="width: 160px" class="wp-caption aligncenter"><a href="../images/2012/03/maler-acryl-150x150.jpg"><img src="../images/2012/03/maler-acryl-150x150.jpg" alt="Acrylic paint" width="" height="" class="size-thumbnail wp-image-17241" /></a><p class="wp-caption-text">Acrylic paint</p></div></td> </tr> </table> <h2>One special problem</h2> <p>As I had a wall plug in my ceiling I needed to remove it before I could start. I could not simply push it into the wall (it didn’t work, I’ve tried it). And removing this special wall plug isn’t that easy. This is how it looks like in the wall:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/hohlraumduebel-zusammen-300x300.jpg"><img src="../images/2012/03/hohlraumduebel-zusammen-300x300.jpg" alt="Zusammengedr&uuml;ckter Hohlraumd&uuml;bel" width="" height="" class="size-medium wp-image-17281" /></a><p class="wp-caption-text">Wall plug</p></div> <p>So I tried to stretch it:</p> <div style="width: 230px" class="wp-caption aligncenter"><a href="../images/2012/03/hohlraumduebel-hammer-220x300.jpg"><img src="../images/2012/03/hohlraumduebel-hammer-220x300.jpg" alt="Stretching the wall plug with the hammer didn&#039;t work" width="" height="" class="size-medium wp-image-17301" /></a><p class="wp-caption-text">Stretching the wall plug with the hammer didn&#039;t work</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/hohlraumduebel-zange-300x300.jpg"><img src="../images/2012/03/hohlraumduebel-zange-300x300.jpg" alt="Stretching the wall plug with a wrench worked ..." width="" height="" class="size-medium wp-image-17311" /></a><p class="wp-caption-text">Stretching the wall plug with a wrench worked ...</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/hohlraumduebel-auseinander-300x300.jpg"><img src="../images/2012/03/hohlraumduebel-auseinander-300x300.jpg" alt="... kind of" width="" height="" class="size-medium wp-image-17341" /></a><p class="wp-caption-text">... kind of</p></div> <h2>Filling the hole</h2> <p>First you need to clean both holes so that the acrylic paint can stick. Then you have to use the masking tape to get a clean border:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/loch-abkleben-300x300.jpg"><img src="../images/2012/03/loch-abkleben-300x300.jpg" alt="Use the masking tape" width="" height="" class="size-medium wp-image-17271" /></a><p class="wp-caption-text">Use the masking tape</p></div> <p>You have to use the putty knife to get a clean, smooth surface with the acrylic paint. Maybe you need to fill the hole repeatedly with acrylic paint. As soon as the surface looks okay, you can stop. Now remove the masking tape and then wait some hours until the acrylic paint is dry. The time you have to wait depends on the acrylic paint you use, but mine is dry enough for painting after 4 - 6 hours.</p> <h2>Situation afterwards</h2> <p>Afterwards, it looks like this:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/03/loch-gefuellt-acryl-300x210.jpg"><img src="../images/2012/03/loch-gefuellt-acryl-300x210.jpg" alt="Filled hole in the ceiling" width="" height="" class="size-medium wp-image-17361" /></a><p class="wp-caption-text">Filled hole in the ceiling</p></div> <p>Hmm … well … it looks different when I look at it. I can barely see it as it’s not that bright at the ceiling. Nether the less, I will have to paint in the summer.</p> Briefe mit LaTeX schreiben //martin-thoma.com/briefe-mit-latex-schreiben/ Sat, 03 Mar 2012 17:48:38 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/briefe-mit-latex-schreiben <p>Ich muss immer wieder mal Kündigungsschreiben aufsetzen. Dafür will ich eigentlich keine Zeit verschwenden, aber es sollte schon gut aussehen. Also habe ich mir gerade mal eine Vorlage für Kündigungsschreiben mit LaTeX und dem scrlttr2 Paket erstellt. Allerdings benutze ich noch die alten KOMA-Variablen. Ich finde mit KOMAold (siehe Beispiel-PDF <a href="../images/2012/03/kuendigung.pdf">alt</a> und <a href="../images/2012/03/kuendigung-scrlttr2.pdf">neu</a>) sieht es einfach besser aus als mit dem neuen. Obwohl der Unterschied nicht wirklich groß ist.</p> <p>Hier ist das <a href="../images/2012/03/kuendigung-archiv.zip">Archiv</a> mit beiden LaTeX-Dateien, einer Make-Datei und beiden PDF-Dateien.</p> <h2>LaTeX</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper, 12pt, KOMAold]{scrlttr2} \usepackage[utf8]{inputenc} % this is needed for umlauts \usepackage[ngerman]{babel} % this is needed for umlauts \usepackage[T1]{fontenc} % needed for right umlaut output in pdf \usepackage[ngerman, num]{isodate} % get DD.MM.YYYY dates % Anpassen %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \newcommand{\Vorname}{Martin} % Vorname % \newcommand{\Nachname}{Thoma} % Nachname % \newcommand{\Strasse}{Parkstra&amp;szlig;e} % Deine Stra&amp;szlig;e % \newcommand{\Hausnummer}{17} % Deine Hausnummer % \newcommand{\PLZ}{76131} % Deine PLZ % \newcommand{\Ort}{Karlsruhe} % Dein Ort % \newcommand{\Kundennr}{123456} % Deine Kundennummer % % \newcommand{\Empfaenger}{DB Fernverkehr AG} % Der Empfänger % \newcommand{\EStrasse}{BahnCard-Service} % Stra&amp;szlig;e des Empfängers % \newcommand{\EPLZ}{60643} % PLZ des Empfängers % \newcommand{\EOrt}{Frankfurt am Main} % Ort des Empfängers % % \newcommand{\DocTitle}{Kündigung des Bahn-Abos} %Titel des Dokuments% % Datum der Kündigung % \newcommand{\Kuendigungsdatum}{nächstmöglichen Termin} % %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% % pdfinfo \pdfinfo{ /Author (\Nachname, \Vorname) /Title (\DocTitle) /Subject (\DocTitle) /Keywords (Kündigung) } % set letter variables \signature{\Vorname~\Nachname} \customer{\Kundennr} \backaddress{\Vorname~\Nachname, \Strasse~\Hausnummer, \PLZ~\Ort} % Begin document %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% \begin{document} \begin{letter}{\Empfaenger \\ \EStrasse \\ \EPLZ~\EOrt} \date{\today}%Change this if you want a different date than today \subject{Kündigung} \opening{Sehr geehrte Damen und Herren,} hiermit kündige ich meinen Vertrag für die Kundennummer \Kundennr~ zum \Kuendigungsdatum.\\ \noindent Ich bitte um eine Bestätigung der Kündigung. \closing{Mit freundlichen Grü&amp;szlig;en,} \end{letter} \end{document} </pre></div> </div> </div> <p>Ach ja, weiß jemand wie man die Einrückung der Unterschrift verhindert?</p> Definitionen aus GBI //martin-thoma.com/definitionen-aus-gbi/ Fri, 02 Mar 2012 16:16:02 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/definitionen-aus-gbi <h2>Formale Sprachen</h2> <p>A heißt Alphabet <code>$:\Leftrightarrow$</code> A ist eine endliche, nicht leere Menge aus Zeichen. w heißt Wort aus <code>$A^* : \Leftrightarrow$</code> w ist eine endliche Aneinanderreihung von Zeichen aus A L heißt formale Sprache <code>$: \Leftrightarrow L \subseteq A^*$</code> G heißt formale Grammatik <code>$: \Leftrightarrow G = (N, T, S, P)$</code> wobei:</p> <ul> <li>N die endliche Menge der Nichtterminalsymbole bezeichne, </li> <li>T die endliche Menge der Terminalsymbole mit `$N \cap T = \emptyset$` bezeichne,</li> <li>`$S \in N$` das Startsymbol,</li> <li>`$P \subseteq N \times (N \cup T)^*$` die endliche Menge der Produktionen bezeichne.</li> </ul> <p>Es seien <code>$L_1$</code> und <code>$L_2$</code> formale Sprachen und <code>$n \in \mathbb{N}$</code>. Dann:</p> <p><code>$L_1 \cdot L_2 :\Leftrightarrow \{w_1 w_2 | w_1 \in L_1 \land w_2 \in L_2\}$</code> <code>$L_1 \cup L_2 :\Leftrightarrow \{w | w \in L_1 \lor w \in L_2\}$</code> <code>$L_1 \cap L_2 :\Leftrightarrow \{w | w \in L_1 \land w \in L_2\}$</code> <code>$L_1 \setminus L_2 :\Leftrightarrow \{w | w \in L_1 \land w \notin L_2\}$</code> <code>$L_1^0 :\Leftrightarrow \{ \varepsilon\}$</code> <code>$L_1^1 :\Leftrightarrow L$</code> <code>$L_1^n :\Leftrightarrow L_1^{n-1} \cdot L_1$</code> <code>$L_1^* :\Leftrightarrow \bigcup_{i=0}^\infty L_1^i$</code> <code>$L_1^+ :\Leftrightarrow L_1^* \setminus L_1^0 = \bigcup_{i=1}^\infty L_1^i$</code></p> <h3>Kodierungstheorie</h3> <p>Seien <code>$L_A, L_B$</code> formale Sprachen und <code>$c: L_A \rightarrow L_B$</code>.</p> <p>c heißt codierung <code>$: \Leftrightarrow$</code> c ist injektiv. <code>$L_B$</code> heißt präfixfrei <code>$: \Leftrightarrow \forall_{u, v, w \in L_B}: uv = w \Rightarrow u = \varepsilon \lor v = \varepsilon$</code></p> <p>Sei <code>$h:A* \rightarrow B*$</code> eine Abbildung. h heißt Homomorphismus <code>$:\Leftrightarrow h(\varepsilon) = \varepsilon \land \forall_{x \in A} \forall_{w \in A*}: h(xw) = h(x)h(w)$</code></p> <h2>Abbildungen und Relationen</h2> <p>Seien A und B Mengen.</p> <p>R heißt binäre Relation von A in B <code>$:\Leftrightarrow R \subseteq A \times B$</code></p> <p>Sei im Folgendem R eine binäre Relation von A in B.</p> <p>R ist linkstotal <code>$:\Leftrightarrow \forall_{a \in A} : \exists_{b \in B} : (a, b) \in R$</code> R ist rechtseindeutig <code>$:\Leftrightarrow \forall_{a \in A} : \forall_{b_1, b_2 \in B: b_1 \neq b_2} : (a, b_1) \in R \Rightarrow (a, b_2) \notin R$</code> R heißt Abbildung <code>$:\Leftrightarrow$</code> R ist linkstotal und rechtseindeutig. Für Abbildungen schreibt man auch: <code>$R: A \rightarrow B$</code>.</p> <p>R heißt linkseindeutig <code>$:\Leftrightarrow \forall_{(a_1, b_1) \in R} : \forall_{(a_2, b_2) \in R} : (a_1, b_1) \in R \Rightarrow (a_2, b_2) \notin R$</code> R heißt injektiv <code>$:\Leftrightarrow$</code> R ist eine linkseindeutige Abbildung. R heißt rechtstotal <code>$:\Leftrightarrow \forall_{b \in B} : \exists_{a \in A} : (a, b) \in R$</code> R heißt surjektiv <code>$:\Leftrightarrow$</code> R ist eine rechtstotale Abbildung. R heißt bijektiv <code>$:\Leftrightarrow$</code> R ist eine injektive und surjektive Abbildung</p> <p>R heißt reflexiv <code>$:\Leftrightarrow \forall_{x \in A} : (x, x) \in R$</code> R heißt symmetrisch <code>$:\Leftrightarrow (x, y) \in R \rightarrow (y, x) \in R$</code> R heißt antisymmetrisch <code>$:\Leftrightarrow (x, y) \in R \land (y, x) \in R \Rightarrow x = y$</code> R heißt transitiv <code>$:\Leftrightarrow (x, y) \in R \land (y, z) \in R \Rightarrow (x, z) \in R$</code></p> <p>R heißt Halbordnung <code>$:\Leftrightarrow$</code> R ist reflexiv, antisymmetrisch und transitiv. Eine Halbordnung ist ein Spezialfall der Ordnungsrelation.</p> <p>R heißt Äquivalenzrelation <code>$:\Leftrightarrow$</code> R ist reflexiv, symmetrisch und transitiv.</p> <p>Sei C eine Menge und <code>$S \subseteq B \times C$</code>. <code>$S \circ R = \{(x,z) \in M_1 \times M_3 | \exists y \in M_2: (x, y) \in R \land (y, z) \in S\}$</code></p> <p>Sei M eine Menge und <code>$R \subseteq M \times M$</code> eine Halbordnung. Dann heißt M halbgeordnet bzw. <code>$(M, R)$</code> halbgeordnete Menge. Sei <code>$T \subseteq M$</code>. <code>$x \in T$</code> heißt minimales Element von T <code>$:\Leftrightarrow$</code> Es gibt kein <code>$y \in T$</code> mit xRy und <code>$x \neq y$</code>. <code>$x \in T$</code> heißt kleinstes Element von T <code>$:\Leftrightarrow$</code> <code>$\forall_{y \in T}: xRy$</code>. Das maximale Element und das größte Element werden analog definiert.</p> <p>R heißt vollständige Halbordnung <code>$:\Leftrightarrow$</code> R ist eine Halbordnung, besitzt ein kleinstes Element und jede aufsteigende Kette besitzt ein Supremum. R heißt Totalordnung <code>$:\Leftrightarrow \forall_{a,b \in M} : aRb \lor bRa$</code></p> <p>Sei <code>$\equiv \subseteq M \times M$</code> eine Äquivalenzrelation, <code>$f : M \rightarrow M$</code> eine Funktion und <code>$\diamond$</code> eine binäre Operation auf der Menge M. <code>$f$</code> heißt verträglich <code>$: \Leftrightarrow \forall_{x,y \in M} : x \equiv y \Rightarrow f(x) \equiv f(y)$</code> <code>$\diamond$</code> heißt verträglich <code>$: \Leftrightarrow \forall_{x_1, x_2,y_1, y_2 \in M} : x_1 \equiv x_2 \land y_1 \equiv y_2 \Rightarrow x_1 \diamond y_1 \equiv x_2 \diamond y_2$</code></p> <h2>Komplexit&auml;tstheorie</h2> <p>Seien <code>$f : \mathbb{N_0} \rightarrow \mathbb{R}^+, g : \mathbb{N_0} \rightarrow \mathbb{R}^+$</code> Funktionen, die die Laufzeit von Algorithmen beschreiben.</p> <p><code>${\cal O}(f(n)) = \{g(n) | \exists_{n_0 \in \mathbb{N}_0} : \exists_{c \in \mathbb{R}^+} : \forall_{n \geq n_0}: g(n) \leq c \cdot f(n)\}$</code> <code>$\Omega(f(n)) = \{g(n) | \exists_{n_0 \in \mathbb{N}_0} : \exists_{c \in \mathbb{R}^+} : \forall_{n \geq n_0}: g(n) \geq c \cdot f(n)\}$</code> <code>$\Theta(f(n)) = \Omega(f(n)) \cap {\cal O}(f(n))$</code></p> <h2>Graphentheorie</h2> <p>G heißt Graph <code>$: \Leftrightarrow G = (V, E)$</code>, wobei V eine endliche Menge an Knoten ist und <code>$E \subseteq V \times V$</code> die Menge der Kanten bezeichne.</p> <p>Sei G = (V, E) ein Graph. G heißt ungerichteter Graph <code>$: \Leftrightarrow \forall_{v_n, v_m \in V} : (v_n, v_m) \in E \Rightarrow (v_m, v_n) \in E$</code> G heißt gerichteter Graph <code>$: \Leftrightarrow$</code> G ist nicht ungerichtet. G heißt streng zusammenhängend <code>$: \Leftrightarrow \forall_{x, y \in V}:$</code> Es gibt einen Pfad von x nach y. G heißt vollständig <code>$: \Leftrightarrow \forall_{x, y \in V}: (x, y) \in E$</code></p> <p>p heißt Pfad in G von <code>$v_0$</code> nach <code>$v_n: \Leftrightarrow p = (v_0, ..., v_n): \forall_{i \in \mathbb{G}_n}: (v_i, v_{i+1}) \in E $</code></p> <p>Ein Knoten <code>$r \in V$</code> heißt Wurzel <code>$: \Leftrightarrow \forall_{x \in V}:$</code> Es gibt genau einen Pfad von r nach x. G heißt Baum <code>$: \Leftrightarrow \exists r \in V: \forall_{x \in V}$</code> Es gibt genau einen Pfad von r nach x.</p> Get your programs assembly code and more information //martin-thoma.com/get-your-programs-assembly-code-and-more-information/ Thu, 01 Mar 2012 19:40:43 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/get-your-programs-assembly-code-and-more-information <p>I’ve talked today with a fellow student about some system internals and we weren’t sure what actually happens. So I needed the assembly code of some example programs.</p> <h2>General Information</h2> <p>It is important to know that I will use <strong>AT&amp;T syntax</strong> in this article! This is AT&amp;T Syntax:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">movl %esp, %ebp</code></pre></div> <p>And this is Intel Syntax:</p> <div class="highlight"><pre><code class="language-text" data-lang="text">MOVL EBP, ESP</code></pre></div> <h3>Pointers</h3> <ul> <li><strong>%esp</strong>: Stack pointer for top address of the stack.</li> <li><strong>%ebp</strong>: Stack base pointer for holding the address of the current stack frame.</li> <li><strong>%eax</strong>: Accumulator</li> </ul> <p>The size of the eax register will always be 32 bit, regardless of the system’s register size.<small><sup><a href="#ref6">[6]</a></sup></small></p> <h3>`$ Dollar and % Percentage signs</h3> <p>$<code>i, with </code>$i \in mathbb{N}$`, is a constant and percentages mean registers.<small><sup><a href="#ref10" name="anchor10">[10]</a></sup></small><small><sup><a href="#ref10" name="anchor11">[11]</a></sup></small></p> <h3>Instruction</h3> <p><strong>pushl <register>&lt;/strong&gt;: To push the source operand onto the stack<small><sup><a href="#ref1" name="anchor1">[1]</a></sup></small> <strong>movl <from>, <to>&lt;/strong&gt;: moves a long<small><sup><a href="#ref2" name="anchor2">[2]</a></sup></small> <strong>call <function>&lt;/strong&gt;: Calls function (which might be printf, putchar, ...) <strong>subl `$16, %esp</strong>: allocate a local variable<small><sup><a href="#ref3" name="anchor3">[3]</a></sup></small> <strong>ret</strong>: transfers control back to the place where the current function was called.<small><sup><a href="#ref3">[3]</a></sup></small> <strong>leave</strong>: sets the stack pointer to the base frame address, effectively releasing the whole frame<small><sup><a href="#ref4" name="anchor4">[4]</a></sup></small> <strong>andl $`-16, %esp</strong>: Ands the stack with fffffff0 which effectivly aligns it on a 16 byte boundary. Access to aligned values on the stack are much faster than if they were unaligned. <small><sup><a href="#ref5" name="anchor5">[5]</a></sup></small> <strong>jmp <target>&lt;/strong&gt;: Jump to target label. <strong>jbe <target>&lt;/strong&gt;: Jump below or equal. I am not quite sure what is compared ... can anybody help me? <strong>leal <command-address> <store>&lt;/strong&gt;: Load effective address.<small><sup><a href="#ref9" name="anchor9">[9]</a></sup></small> The LEA instruction never reads memory, it only computes the address that would be read by another instruction and stores this address in its first register operand.</store></command-address></strong></target></strong></target></strong></function></strong></to></from></strong></register></strong></p> <h4>Suffixes</h4> <p>Many instructions have suffixes. This is what they mean<small><sup><a href="#ref6" name="anchor6">[6]</a></sup></small>:</p> <ul> <li>b: byte (8 bit)</li> <li>s: short (16 bit integer) or single (32-bit floating point)</li> <li>w: word (16 bit)</li> <li>l: long (32 bit integer or 64-bit floating point)</li> <li>q: quad (64 bit)</li> <li>t: ten bytes (80-bit floating point)</li> </ul> <h2>Simple example</h2> <h3>C-Code</h3> <p>This program simply outputs</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">void</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;%i&quot;</span><span class="p">,</span> <span class="mi">1337</span><span class="o">*</span><span class="mi">42</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h3>Assembly</h3> <p>Now I compile it and I save the assembly code:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">gcc -S test.c<span class="p">;</span> gcc test.c -o <span class="nb">test</span></code></pre></div> <p>This gives me test.s (the assembly code) and an executable called “test”.</p> <div class="highlight"><pre><code class="language-text" data-lang="text">.file &quot;test.c&quot; .section .rodata .LC0: .string &quot;%i&quot; .text .globl main .type main, @function main: pushl %ebp movl %esp, %ebp andl `$-16, %esp subl $`16, %esp movl `$.LC0, %eax movl $`56154, 4(%esp) movl %eax, (%esp) call printf movl `$0, %eax leave ret .size main, .-main .ident &quot;GCC: (Ubuntu 4.4.3-4ubuntu5) 4.4.3&quot; .section .note.GNU-stack,&quot;&quot;,@progbits</code></pre></div> <p>This is code of the <a href="http://en.wikipedia.org/wiki/GNU_Assembler">GNU Assembler</a>. I guess other assemblers might produce other code. Could anybody please give me an example of other assemblers?</p> <p>The first and most important thing you might notice is that neither “1337” nor “42” appear in the assembly code, but 56154 which is 1337*42. I didn’t use any optimization options! You might also notice that constants begin with a dollar sign and registers (esp, ebp) begin with a percent sign.</p> <p>The following ones are called assembly directives. They tell the assembler what to do next. <a href="http://tigcc.ticalc.org/doc/gnuasm.html#SEC90">.file</a>, <a href="http://tigcc.ticalc.org/doc/gnuasm.html#SEC119">.section</a>, <a href="http://tigcc.ticalc.org/doc/gnuasm.html#SEC123">.size</a> and <a href="http://tigcc.ticalc.org/doc/gnuasm.html#SEC95">.ident</a> are such directives. .data might be the most well-known one and tells the assembler to store something in the data segment of the program. .LC0 is a label for the immediately following string. .globl indicates that the following label (in this case “main”) is a global symbol.</p> <p>Line 14: I’m not quite sure why you need the 4. I thought the integer size could be the reason (see <a href="http://www.cplusplus.com/doc/tutorial/variables/">variable sizes in C</a>), but as I used a string it still worked. As I used a character, it disappeared.</p> <h3>Further information</h3> <p><code>objdump</code> gives even more information!</p> <p>Archive header information: objdump -a test</p> <div class="highlight"><pre><code class="language-text" data-lang="text">test: file format elf32-i386 test</code></pre></div> <p>File header information: objdump -f test</p> <div class="highlight"><pre><code class="language-text" data-lang="text">test: file format elf32-i386 architecture: i386, flags 0x00000112: EXEC_P, HAS_SYMS, D_PAGED start address 0x08048330</code></pre></div> <p>Object specific file header contents: objdump -p test</p> <div class="highlight"><pre><code class="language-text" data-lang="text">test: file format elf32-i386 Program Header: PHDR off 0x00000034 vaddr 0x08048034 paddr 0x08048034 align 2**2 filesz 0x00000100 memsz 0x00000100 flags r-x INTERP off 0x00000134 vaddr 0x08048134 paddr 0x08048134 align 2**0 filesz 0x00000013 memsz 0x00000013 flags r-- LOAD off 0x00000000 vaddr 0x08048000 paddr 0x08048000 align 2**12 filesz 0x000004d8 memsz 0x000004d8 flags r-x LOAD off 0x00000f0c vaddr 0x08049f0c paddr 0x08049f0c align 2**12 filesz 0x00000108 memsz 0x00000110 flags rw- DYNAMIC off 0x00000f20 vaddr 0x08049f20 paddr 0x08049f20 align 2**2 filesz 0x000000d0 memsz 0x000000d0 flags rw- NOTE off 0x00000148 vaddr 0x08048148 paddr 0x08048148 align 2**2 filesz 0x00000044 memsz 0x00000044 flags r-- STACK off 0x00000000 vaddr 0x00000000 paddr 0x00000000 align 2**2 filesz 0x00000000 memsz 0x00000000 flags rw- RELRO off 0x00000f0c vaddr 0x08049f0c paddr 0x08049f0c align 2**0 filesz 0x000000f4 memsz 0x000000f4 flags r-- Dynamic Section: NEEDED libc.so.6 INIT 0x080482bc FINI 0x080484ac HASH 0x0804818c GNU_HASH 0x080481b4 STRTAB 0x08048224 SYMTAB 0x080481d4 STRSZ 0x0000004c SYMENT 0x00000010 DEBUG 0x00000000 PLTGOT 0x08049ff4 PLTRELSZ 0x00000018 PLTREL 0x00000011 JMPREL 0x080482a4 REL 0x0804829c RELSZ 0x00000008 RELENT 0x00000008 VERNEED 0x0804827c VERNEEDNUM 0x00000001 VERSYM 0x08048270 Version References: required from libc.so.6: 0x0d696910 0x00 02 GLIBC_2.0</code></pre></div> <p>Display the contents of the section headers: objdump -h test</p> <div class="highlight"><pre><code class="language-text" data-lang="text">test: file format elf32-i386 Sections: Idx Name Size VMA LMA File off Algn 0 .interp 00000013 08048134 08048134 00000134 2**0 CONTENTS, ALLOC, LOAD, READONLY, DATA 1 .note.ABI-tag 00000020 08048148 08048148 00000148 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 2 .note.gnu.build-id 00000024 08048168 08048168 00000168 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 3 .hash 00000028 0804818c 0804818c 0000018c 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 4 .gnu.hash 00000020 080481b4 080481b4 000001b4 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 5 .dynsym 00000050 080481d4 080481d4 000001d4 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 6 .dynstr 0000004c 08048224 08048224 00000224 2**0 CONTENTS, ALLOC, LOAD, READONLY, DATA 7 .gnu.version 0000000a 08048270 08048270 00000270 2**1 CONTENTS, ALLOC, LOAD, READONLY, DATA 8 .gnu.version_r 00000020 0804827c 0804827c 0000027c 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 9 .rel.dyn 00000008 0804829c 0804829c 0000029c 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 10 .rel.plt 00000018 080482a4 080482a4 000002a4 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 11 .init 00000030 080482bc 080482bc 000002bc 2**2 CONTENTS, ALLOC, LOAD, READONLY, CODE 12 .plt 00000040 080482ec 080482ec 000002ec 2**2 CONTENTS, ALLOC, LOAD, READONLY, CODE 13 .text 0000017c 08048330 08048330 00000330 2**4 CONTENTS, ALLOC, LOAD, READONLY, CODE 14 .fini 0000001c 080484ac 080484ac 000004ac 2**2 CONTENTS, ALLOC, LOAD, READONLY, CODE 15 .rodata 0000000b 080484c8 080484c8 000004c8 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 16 .eh_frame 00000004 080484d4 080484d4 000004d4 2**2 CONTENTS, ALLOC, LOAD, READONLY, DATA 17 .ctors 00000008 08049f0c 08049f0c 00000f0c 2**2 CONTENTS, ALLOC, LOAD, DATA 18 .dtors 00000008 08049f14 08049f14 00000f14 2**2 CONTENTS, ALLOC, LOAD, DATA 19 .jcr 00000004 08049f1c 08049f1c 00000f1c 2**2 CONTENTS, ALLOC, LOAD, DATA 20 .dynamic 000000d0 08049f20 08049f20 00000f20 2**2 CONTENTS, ALLOC, LOAD, DATA 21 .got 00000004 08049ff0 08049ff0 00000ff0 2**2 CONTENTS, ALLOC, LOAD, DATA 22 .got.plt 00000018 08049ff4 08049ff4 00000ff4 2**2 CONTENTS, ALLOC, LOAD, DATA 23 .data 00000008 0804a00c 0804a00c 0000100c 2**2 CONTENTS, ALLOC, LOAD, DATA 24 .bss 00000008 0804a014 0804a014 00001014 2**2 ALLOC 25 .comment 00000023 00000000 00000000 00001014 2**0 CONTENTS, READONLY</code></pre></div> <p>Display DWARF info in the file: objdump –dwarf test</p> <div class="highlight"><pre><code class="language-text" data-lang="text">test: file format elf32-i386 Contents of the .eh_frame section: 00000000 ZERO terminator</code></pre></div> <p>By the way, <a href="http://en.wikipedia.org/wiki/Executable_and_Linkable_Format">ELF</a> is an executable file format and <a href="http://en.wikipedia.org/wiki/DWARF">DWARF</a> is a debugging file format. I guess they had to think quite long to find this <a href="http://en.wikipedia.org/wiki/Backronym">backronym</a>.</p> <h2>Fibonacci</h2> <h3>C-Code</h3> <p>This is the most simple version of Fibonacci I could find:<small><sup><a href="#ref7" name="anchor7">[7]</a></sup></small></p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">unsigned</span> <span class="kt">int</span> <span class="nf">fib</span><span class="p">(</span><span class="kt">unsigned</span> <span class="kt">int</span> <span class="n">n</span><span class="p">)</span> <span class="p">{</span> <span class="k">return</span> <span class="n">n</span> <span class="o">&lt;</span> <span class="mi">2</span> <span class="o">?</span> <span class="nl">n</span> <span class="p">:</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">2</span><span class="p">);</span> <span class="p">}</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">(</span><span class="kt">void</span><span class="p">)</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;%i&quot;</span><span class="p">,</span> <span class="n">fib</span><span class="p">(</span><span class="mi">13</span><span class="p">));</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <h3>Assembly</h3> <div class="highlight"><pre><code class="language-text" data-lang="text">.file &quot;test.c&quot; .text .globl fib .type fib, @function fib: pushl %ebp movl %esp, %ebp pushl %ebx subl $`20, %esp cmpl `$1, 8(%ebp) jbe .L2 movl 8(%ebp), %eax subl $`1, %eax movl %eax, (%esp) call fib movl %eax, %ebx movl 8(%ebp), %eax subl `$2, %eax movl %eax, (%esp) call fib leal (%ebx,%eax), %eax jmp .L3 .L2: movl 8(%ebp), %eax .L3: addl $`20, %esp popl %ebx popl %ebp ret .size fib, .-fib .section .rodata .LC0: .string &quot;%i&quot; .text .globl main .type main, @function main: pushl %ebp movl %esp, %ebp andl `$-16, %esp subl $`16, %esp movl `$13, (%esp) call fib movl $`.LC0, %edx movl %eax, 4(%esp) movl %edx, (%esp) call printf movl `$0, %eax leave ret .size main, .-main .ident &quot;GCC: (Ubuntu 4.4.3-4ubuntu5) 4.4.3&quot; .section .note.GNU-stack,&quot;&quot;,@progbits</code></pre></div> <h2>References</h2> <ol> <li><a name="ref1" href="#anchor1">&uarr;</a>: <a href="http://www.cs.auckland.ac.nz/references/macvax/op-codes/Instructions/pushl.html">PUSHL Instruction</a>. The University of Auckland, Department of Computer Science.</li> <li><a name="ref2" href="#anchor2">&uarr;</a>: <a href="http://www.cse.nd.edu/~dthain/courses/cse40243/fall2008/ia32-intro.html">IA-32 Assembly for Compiler Writers</a>. Douglas Thain, Associate Professor, University of Notre Dame, Department of Computer Science and Engineering.</li> <li><a name="ref3" href="#anchor3">&uarr;</a>: <a href="http://linuxgazette.net/issue94/ramankutty.html">From C To Assembly Language </a>. Hiran Ramankutty, Linux Gazett, Issue 94.</li> <li><a name="ref4" href="#anchor4">&uarr;</a>: <a href="http://stackoverflow.com/questions/5474355/about-leave-in-x86-assembly">About leave in x86 assembly</a>. zneak, Stackoverflow.</li> <li><a name="ref5" href="#anchor5">&uarr;</a>: <a href="http://stackoverflow.com/a/1317324/562769">GCC's assembly output of an empty program on x86, win32</a>. nos, Stackoverflow.</li> <li><a name="ref6" href="#anchor6">&uarr;</a>: <a href="http://stackoverflow.com/a/1898896/562769">Why would one use &ldquo;movl $`1, %eax&rdquo; as opposed to, say, &ldquo;movb `$1, %eax&rdquo;</a>. Jason, Stackoverflow.</li> <li><a name="ref7" href="#anchor7">&uarr;</a>: <a href="http://en.literateprograms.org/Fibonacci_numbers_%28C%29#Recursive">Fibonacci numbers (C)</a>. Literate Programs.</li> <li><a name="ref8" href="#anchor8">&uarr;</a>: <a href="http://wpage.unina.it/rcanonic/didattica/ce1/docs/68000.pdf"> The 68000's Instruction Set</a>, page 27. Literate Programs.</li> <li><a name="ref9" href="#anchor9">&uarr;</a>: <a href="http://stackoverflow.com/questions/4003894/leal-assembler-instruction">LEAL Assembler instruction</a>. Nils Pipenbrinck, Stackoverflow</li> <li><a name="ref10" href="#anchor10">&uarr;</a>: <a href="http://stackoverflow.com/a/5367004/562769">What does this dollar sign mean in __asm?</a>. Zimbabao, Stackoverflow</li> <li><a name="ref11" href="#anchor11">&uarr;</a>: <a href="http://stackoverflow.com/a/9196757/562769">What do the dollar ($`) and percentage (%) signs represent in assembly intel x86?</a>. Necrolis, Stackoverflow</li> </ol> Creating pdf-forms with LaTeX //martin-thoma.com/creating-pdf-forms-with-latex/ Wed, 29 Feb 2012 15:11:07 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/creating-pdf-forms-with-latex <p>I’ve just stumbled across a full, working example how to create a html form within an LaTeX document. You can fill this form within your PDF-Reader. Here is the <a href="../images/2012/02/pdf-form.pdf">example PDF-file</a>.</p> <p>It looks like this in Chromes PDF reader:</p> <div style="width: 431px" class="wp-caption aligncenter"><a href="../images/2012/02/pdf-latex-form-chrome.png"><img src="../images/2012/02/pdf-latex-form-chrome.png" alt="PDF LaTeX form in Chrome" width="" height="" class="size-full wp-image-16711" /></a><p class="wp-caption-text">PDF LaTeX form in Chrome</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,12pt]{article} \usepackage{amssymb} % needed for math \usepackage{amsmath} % needed for math \usepackage[utf8]{inputenc} % this is needed for german umlauts \usepackage[ngerman]{babel} % this is needed for german umlauts \usepackage[T1]{fontenc} % this is needed for correct output of umlauts in pdf \usepackage[margin=2.5cm]{geometry} %layout \usepackage{hyperref} % this is needed for forms and links within the text \hypersetup{ pdfauthor = {Martin Thoma}, pdfkeywords = {Martin Thoma, exmple, LaTeX, form}, pdftitle = {An example for a LaTeX form} } \begin{document} \title{An example for a LaTeX form} \author{Martin Thoma} \date{\today} \section{An example for a \LaTeX~form} \begin{Form}[action=mailto:info@example.com,encoding=html,method=post] \subsection{Some general information:} \begin{tabbing} xxxxxxxxxx: \= \kill % This is needed for the right tab width Name: \&gt; \TextField[name=name,width=3cm,charsize=12pt] {\mbox{}} Prename: \TextField[name=vor,width=3cm,charsize=12pt] {\mbox{}} \\ City: \&gt; \ChoiceMenu[combo,name=city,width=5cm,charsize=12pt,default=Karlsruhe]{\mbox{}} {Chemnitz,Dresden,Leipzig,Berlin,Hamburg,Karlsruhe,M&amp;uuml;nchen} \\ Sex: \&gt; \ChoiceMenu[radio,default=f,name=sex,charsize=14pt]{\mbox{}}{Male=m,Female=f} \end{tabbing} \subsection{Education:} \CheckBox[name=highschool,charsize=12pt]{High School} \CheckBox[name=college,charsize=12pt]{College} \CheckBox[name=university,charsize=12pt]{University} \\ \Submit{Submit} \Reset{Clear} \hfill ~\\ \end{Form} \end{document} </pre></div> </div> </div> <p>You can save this as pdf-form.tex and run this command in Linux:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pdflatex pdf-form.tex -output-format<span class="o">=</span>pdf</code></pre></div> <p>It seems as if the \ChoiceMenu radio option is buggy at the moment. Does anybody know how to fix that? edit: Hmm … it works in Chromes PDF reader, but not in Document Viewer. Mayby Document Viewer is buggy.</p> <h2>Sources</h2> <ul> <li>TeX Users Group: <a href="http://www.tug.org/applications/hyperref/manual.html#x1-190006">PDF and HTML forms</a></li> <li><a href="http://www.qucosa.de/fileadmin/data/qucosa/documents/4512/data/vortrag2.pdf">Teil 2: LATEX und PDF</a> - TU Chemnitz (German)</li> <li><a href="http://www2.informatik.hu-berlin.de/~piefel/LaTeX-PS/Archive-2004/V12-PDF.pdf">Dokumentation der HU Berlin</a> (German)</li> </ul> GBI-Klausur //martin-thoma.com/gbi-klausur/ Tue, 28 Feb 2012 19:30:01 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/gbi-klausur <p>Für die Klausur in den Grundbegriffe der Informatik (GBI) sollte man Folgendes auf jeden Fall wissen:</p> <ul> <li>Wie funktionieren Induktionsbeweise? &rarr; <a href="../wie-fuhre-ich-einen-induktionsbeweis/" title="Wie f&uuml;hre ich einen Induktionsbeweis?">Antwort</a></li> <li>Was ist ein Alphabet, eine formale Sprache und was eine formale Grammatik? &rarr; <a href="../definitionen-aus-gbi/#Formale_Sprachen" title="Definitionen aus GBI">Antwort</a></li> <li>Was bedeuten f&uuml;r zwei Formale Sprachen `$L_1, L_2$` folgende bin&auml;ren Operationen:`$\cdot, \cup, \cap, \setminus, L_1^3, L^+, L^*$`? &rarr; <a href="../definitionen-aus-gbi/#Formale_Sprachen" title="Definitionen aus GBI">Antwort</a></li> <li>Was ist eine Abbildung, was eine Relation? &rarr; <a href="../definitionen-aus-gbi/#Abbildungen_und_Relationen" title="Definitionen aus GBI">Antwort</a></li> <li>Was ist Injektivit&auml;t, Surjektivit&auml;t, Bijektivit&auml;t, Reflexivit&auml;t, Symmetrie, Antisymmetrie und Transitivit&auml;t? &rarr; <a href="../definitionen-aus-gbi/#Abbildungen_und_Relationen" title="Definitionen aus GBI">Antwort</a></li> <li>Wie ist eine &Auml;quivalenzrelation, eine Ordnungsrelation, eine Halbordnung und eine Totalordnung definiert? &rarr; <a href="../definitionen-aus-gbi/#Abbildungen_und_Relationen" title="Definitionen aus GBI">Antwort</a></li> <li>Wie ist ein minimales Element und wie das kleinste Element einer Halbordnung definiert? &rarr; <a href="../definitionen-aus-gbi/#Abbildungen_und_Relationen" title="Definitionen aus GBI">Antwort</a></li> <li>Wie sind die Landau-Symbole `$\cal O(f(n)), \Theta(f(n)), \Omega(f(n))$` definiert? &rarr; <a href="../definitionen-aus-gbi/#Komplexittstheorie" title="Definitionen aus GBI">Antwort</a> und <a href="../die-landau-symbole/">Nachtrag</a></li> <li>Was ist eine Turingmaschine und wie gibt man eine Konfiguration davon an?</li> <li>Wie ist ein Graph definiert und wie ein Baum? &rarr; <a href="../definitionen-aus-gbi/#Graphen" title="Definitionen aus GBI">Antwort</a></li> <li>Wann sind zwei Graphen isomorph?</li> <li>Was ist eine Pfad, eine Schlinge, ein Kreis und ein Zyklus?</li> <li>Wann ist ein Graph zusammenh&auml;ngend und wann vollst&auml;ndig / streng zusammenh&auml;ngend?</li> <li>Was ist eine Adjazenzmatrix und was ist eine Wegematrix?</li> <li>Wie lautet die Wahrheitstabelle von `$A \Rightarrow B$`?</li> <li>Wie unterscheiden sich Mealy- und Moore-Automaten? Welche Sprachen akzeptieren sie und wie stellt man sie dar?</li> <li>Was ist eine Huffman-Kodierung und wie stellt man sie dar?</li> <li>Was haben alle W&ouml;rter einer &Auml;quivalenzklasse der Nerode-Relation gemeinsam?</li> <li>Was ist ein Hasse-Diagramm?</li> <li>Wie lautet das Master-Theorem? &rarr; <a href="http://de.wikipedia.org/wiki/Master-Theorem#Allgemeine_Form">Antwort</a></li> </ul> <p>Wenn die Antwort auf eine dieser Fragen noch unklar ist, sollte man sich das <a href="http://gbi.ira.uka.de/vorlesungen/skript.pdf">Skript</a> nochmals anschauen.</p> <p>Was man auf jeden Fall üben sollte, sind die Aufgaben zu Turingmaschinen. Das kommt sicher dran und man ist sicher zu langsam, wenn man nicht ein paar Aufgaben dazu macht.</p> <h2>Some Random Facts</h2> <ul> <li>Ein Mebibyte (MiB) sind `$2^{20}$` Byte, ein Megabyte (MB) sind `$10^6$` Byte.</li> <li>`$\{\varepsilon\} \neq \emptyset = \{\}$`</li> <li>`$\cal P(\emptyset) = \{\emptyset\} = \{\{\}\}$` und `$|{\cal P}(\emptyset)| = 1$`, aber `$|\emptyset| = 0$`.</li> <li>`$Num_2(111)$` ist die Zahl 7, `$Repr_2$`(die Zahl 7) = 111</li> <li>`$\langle \emptyset \rangle = \{\}$` und `$\langle \emptyset * \rangle = \{\varepsilon\}$`</li> <li>Ein paar Beziehungen von Komplexit&auml;tsklassen: <ul> <li>`${\cal O}(\log(n)) \subsetneq {\cal O}(n)$`</li> <li>`${\cal O}(n^{2.1}) \subsetneq {\cal O}(n^{2.2})$`</li> <li>`${\cal O}(n^{100}) \subsetneq {\cal O}(n!)$`</li> <li>`${\cal O}(2^n) \subsetneq {\cal O}(n!) \subsetneq {\cal O}(n^n) \subsetneq {\cal O}(2^{n^2})$`</li> <li>`${\cal O}((n^n)^n) \subsetneq {\cal O}(n^{(n^3)})$`</li> </ul> </li> <li>Logarithmusgesetze: <ul> <li>`$\log(x \cdot y) = \log(x) + \log(y)$`</li> <li>`$\log(\frac{x}{y}) = \log(x) - \log(y)$`</li> <li>`$\log(x^r) = r \cdot \log(x)$`</li> </ul> </li> <li>Ein minimaler Endlicher Automat zu einer regul&auml;re Sprache L hat n Zust&auml;nde `$\Leftrightarrow$` Es gibt n &Auml;quivalenzklassen bzgl. der Nerode-Relation zu L.</li> <li>Der Index der Nerode-Relation zu einer Sprache L ist nicht endlich `$\Leftrightarrow$` L ist nicht regul&auml;r</li> <li>`$S \circ R = \{(x, z) \in M_1 \times M_3 | \exists y \in M_2: (x, y) \in R \land (y, z) \in S\}$`</li> <li>r ist Wurzel von `$G = (V, E) \Leftrightarrow \forall x \in V : $` Es gibt genau einen Pfad von r nach x.</li> </ul> <p>Zum Üben habe ich mal eine “Klausur” erstellt. Hier ist die <a href="../images/2012/02/gbi-klausurvorbereitung.pdf">PDF</a> und hier die <a href="../images/2012/02/gbi-klausurvorbereitung.zip">LaTeX</a>-Datei.</p> <h3>Gro&szlig;-O-Notation</h3> <p><strong>Beh</strong>: <code>$\mathcal{O}(n!) \nsubseteq \mathcal{O}(2^n)$</code></p> <p><strong>Bew</strong>: z.Z.: <code>$n! \notin \mathcal{O}(2^n)$</code></p> <p>Annahme: <code>$\exists c \in \mathbb{R}: n! \leq c \cdot 2^n$</code></p> <p><code>$n! \leq c \cdot 2^n\\ \Leftrightarrow \frac{n!}{2^n} \leq c\\ \Leftrightarrow \frac{\Pi_{i=1}^n i}{\Pi_{i=1}^n 2} \leq c\\ \Leftrightarrow \Pi_{i=1}^n \frac{i}{2} \leq c$</code></p> <p>Es gilt: <code>$\Pi_{i=1}^n \frac{i}{2} = \frac{1}{2} \cdot 1 \cdot \frac{3}{2} \Pi_{i=4}^n \frac{i}{2} \ge \frac{3}{4} \cdot 2^n $</code> <code>$\Rightarrow \forall c \in \mathbb{R} \exists n_0 \in \mathbb{N} \forall n \geq n_0: n! \geq c \cdot 2^n$</code></p> <p>Offensichtlich ist also <code>$\mathcal{O}(n!) \nsubseteq \mathcal{O}(2^n)$</code>.</p> <h2>Formalismen</h2> <ul> <li>Ableitungen benutzen Doppelpfeile, Ableitungsregeln einfache Pfeile.</li> <li>Bei ungerichteten Graphen werden die Kanten also Mengen mit zwei Elementen beschrieben, bei gerichteten als Tupel.</li> </ul> <h2>Termin</h2> <p>Alle wichtigen Informationen stehen auf der <a href="http://gbi.ira.uka.de/pruefungen/klausuren.html">Klausurseite</a>.</p> <ul> <li><strong>Datum</strong>: 05.03.2012 um 11:00 Uhr. Anwesend sollte man ab ca. 10:30 - 10:40 Uhr sein.</li> <li><strong>Ort</strong>: <a href="http://gbi.ira.uka.de/pruefungen/hoersaal_einteilung_gbi_2012.pdf">Liste der Zuweisung</a> - Das sind ganze 729 Matrikelnummern! (Ich schreib im Benz).</li> <li><strong>Dauer</strong>: 120 min.</li> <li><strong>Punkte</strong>: 40 - 50, mit der Hälfte hat man auf jeden Fall bestanden.</li> <li><strong>Nicht vergessen</strong>: Studentenausweis</li> <li><strong>Nachklausur</strong>: am 18.09.2012. Hinweise sind <a href="http://www.informatik.kit.edu/klausuren.php?kid=388.35">hier</a>.</li> </ul> <h2>Ergebnisse</h2> <p>Die <a href="http://gbi.ira.uka.de/pruefungen/aushang.pdf">Ergebnisse</a> sind nun hier verfügbar.</p> <p>Das ist eine Notenverteilung, die mir ein Kommilitone zugeschickt hat:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/02/gbi-ergebnisse-300x231.jpg"><img src="../images/2012/02/gbi-ergebnisse-300x231.jpg" alt="GBI Ergebnisse" width="" height="" class="size-medium wp-image-19301" /></a><p class="wp-caption-text">GBI Ergebnisse</p></div> Stuxnet //martin-thoma.com/stuxnet/ Fri, 24 Feb 2012 09:35:04 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/stuxnet <p>The following clip is a nice, short explanation of <a href="http://en.wikipedia.org/wiki/Stuxnet">Stuxnet</a>, a computer worm discovered in June 2010:</p> <iframe src="http://player.vimeo.com/video/25118844?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> Portal - Still Alive typography clip //martin-thoma.com/portal-still-alive-typography-clip/ Thu, 23 Feb 2012 21:29:48 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/portal-still-alive-typography-clip <iframe src="http://player.vimeo.com/video/1612411?title=0&amp;byline=0&amp;portrait=0" width="512" height="307" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> 7 mind-blowing artists you didn't know //martin-thoma.com/7-mind-blowing-artists-you-didnt-know/ Thu, 23 Feb 2012 19:56:14 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/7-mind-blowing-artists-you-didnt-know <h2>Anamorphic Art</h2> <p><a href="http://en.wikipedia.org/wiki/Anamorphosis">Anamorphosis</a> is a distorted projection or perspective requiring the viewer to use special devices or occupy a specific vantage point to reconstitute the image.</p> <p>Here is a good example by <a href="http://www.varini.org/">Felice Varini</a>:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/02/anamorphic-art.png"><img src="../images/2012/02/anamorphic-art.png" alt="Anamorphic Art" width="" height="" class="size-full wp-image-15541" /></a><p class="wp-caption-text">Anamorphic Art - Source: illusion.scene360.com</p></div> <h2>Pavement Drawings</h2> <p>Pavement Drawings can be combined with anamorphic art. One great artist I’ve found is <a href="http://www.julianbeever.net/pave.htm">Julian Beever</a>. Here is one example:</p> <div style="width: 460px" class="wp-caption aligncenter"><a href="../images/2012/02/pavement-drawing-snail.jpg"><img src="../images/2012/02/pavement-drawing-snail.jpg" alt="Pavement Drawing by Julian Beever" width="" height="" class="size-full wp-image-15561" /></a><p class="wp-caption-text">Pavement Drawing by Julian Beever</p></div> <h2>Hand Painting</h2> <p>You might already know body painting. <a href="http://www.guidodaniele.com/?page_id=8">Guido Daniele</a> does something very simmilar he calls “Hand Painting”. Here is one example:</p> <div style="width: 519px" class="wp-caption aligncenter"><a href="../images/2012/02/hand-art-guido-daniele.jpg"><img src="../images/2012/02/hand-art-guido-daniele.jpg" alt="Hand Painting by Guido Daniele" width="" height="" class="size-full wp-image-15571" /></a><p class="wp-caption-text">Hand Painting by Guido Daniele</p></div> <h2>Hair Sculptures</h2> <p><a href="http://en.wikipedia.org/wiki/Willard_Wigan">Willard Wigan</a> is a sculptor from Birmingham, England, who makes microscopic art. His sculptures are typically placed in the eye of a needle or on the head of a pin. A single sculpture can be as small as 0.005 mm. Here is an example from his <a href="http://www.willard-wigan.com/gallery.aspx">gallery</a>:</p> <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2012/02/Harry-Potter.jpg"><img src="../images/2012/02/Harry-Potter.jpg" alt="Harry Potter by Willard Wigan" width="" height="" class="size-full wp-image-15601" /></a><p class="wp-caption-text">Harry Potter by Willard Wigan</p></div> <h2>Sand Art</h2> <p>It is amazing what can be done with sand. <a href="http://en.wikipedia.org/wiki/Sudarshan_Pattnaik">Sudarsan Pattnaik</a> created this sculpture:</p> <div style="width: 479px" class="wp-caption aligncenter"><a href="../images/2012/02/sand-art-global-warming-sudarshan-pattnaik.jpg"><img src="../images/2012/02/sand-art-global-warming-sudarshan-pattnaik.jpg" alt="Sand Art: Global Warming by Sudarshan Pattnaik" width="" height="" class="size-full wp-image-15621" /></a><p class="wp-caption-text">Sand Art: Global Warming by Sudarshan Pattnaik</p></div> <h2>Origami</h2> <p>Robert J. Lang seems to invest a serious amount of time in <a href="http://en.wikipedia.org/wiki/Origami">Origami</a>. His <a href="http://www.langorigami.com/art/gallery/gallery.php?tag=mammals&amp;name=bull_moose">gallery of mammals</a> is very impressive. Here is a moose:</p> <div style="width: 378px" class="wp-caption aligncenter"><a href="../images/2012/02/lang-origami-moose.png"><img src="../images/2012/02/lang-origami-moose.png" alt="Origami moose by Robert J. Lang" width="" height="" class="size-full wp-image-15651" /></a><p class="wp-caption-text">Origami moose by Robert J. Lang</p></div> <h2>Domino Day</h2> <p>This is not done by one artist, but it should be mentioned:</p> <iframe width="512" height="377" src="http://www.youtube.com/embed/yeF7yLkEECs" frameborder="0" allowfullscreen=""></iframe> TGI-Klausur //martin-thoma.com/tgi-klausur/ Sat, 18 Feb 2012 16:57:30 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/tgi-klausur <div class="info">Ich habe im WS 2011/2012 bei Frau <a href="http://i11www.iti.uni-karlsruhe.de/en/members/dorothea_wagner/index">Prof. Dr. Wagner</a> die TGI-Klausur am KIT geschrieben. Hierf&uuml;r entstand dieser Artikel.</div> <p>Für die Klausur in den Theoretischen Grundlagen der Informatik sollte man Folgendes auf jeden Fall wissen:</p> <ul> <li>Wie konstruiert man mittels <strong>Potenzmengen</strong> einen &auml;quivalenten deterministischen endlichen Automaten zu einem Nichtdeterministischen? &rarr; <a href="../konstruktion-eines-deterministischen-endlichen-automaten-aus-einem-nicht-deterministischem/" title="Konstruktion eines deterministischen endlichen Automaten aus einem nicht-deterministischem">Antwort</a></li> <li>Wie bringt man eine Grammatik in <strong>Chomsky-Normalform</strong>? &rarr; <a href="../konstruktion-der-chomsky-normalform/" title="Konstruktion der Chomsky-Normalform">Antwort</a>.</li> <li>Was macht der <strong>CYK-Algorithmus</strong> und wie funktioniert er? &rarr; siehe <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/uebung7.pdf">Beispiel</a> ab Folie 15</li> <li>Was ist die <strong>Chomsky-Hirarchie</strong>, welche Grammatiken gibt es und mit welchen Operationen sind sie <strong>Abgeschlossen</strong>? &rarr; <a href="../sprachen-automaten-und-grammatiken/" title="Sprachen, Automaten und Grammatiken: Ein &Uuml;berblick">Antwort</a>.</li> <li>Was ist das Post'sche Korrespondenzproblem?</li> <li>Welche <strong>Komplexit&auml;tsklassen</strong> sind `$\cal P, NP, NPC, DTAPE, NTAPE, NPI$`? &rarr; <a href="../komplexitatsklassen-in-der-informatik-ein-uberblick/" title="Komplexit&auml;tsklassen in der Informatik: Ein &Uuml;berblick">Antwort</a></li> <li>Wie sind <strong>Kellerautomaten</strong> definiert, wann sind sie formal nicht-deterministisch und in welcher Beziehung stehen sie zur Greibach-Normalform? Wie formt man einen Kellerautomaten von einem akzeptierenden Endzustand in einen mit leerem Stack um? &rarr; <a href="../kellerautomat/" title="Kellerautomat">Antwort</a>.</li> <li>Wie lautet das <strong>Pumping-Lemma</strong> (f&uuml;r regul&auml;re und kontextfreie Sprachen? Wie lautet <strong>Ogdens Lemma</strong>? Und wie benutzt man diese f&uuml;r Beweise? &rarr; <a href="../pumping-lemma/" title="Eine Sprache ist nicht regul&auml;r &ndash; Beweis mit dem Pumping-Lemma">Antwort</a></li> <li>Wie beweist man <strong>NP-Vollst&auml;ndigkeit</strong>?</li> </ul> <h2>Some Random Facts</h2> <ul> <li>"aaa" ist in der Sprache aller Worter, die zwei mal "aa" enthalten. <small><sup><a href="#ref1" name="anchor1">[1]</a></sup></small></li> <li>Die Grammatik `$G_1(\{S\}, \{\varepsilon\}, \{S \rightarrow \varepsilon\},S)$` erzeugt die Sprache `$L(G_1) = \{\varepsilon\}$`.<small><sup><a href="#ref2" name="anchor2">[2]</a></sup></small></li> <li>Die Grammatik `$G_2(\{S\}, \{\varepsilon\}, \{\},S)$` erzeugt die Sprache `$L(G_2) = \{\}$`.</li> <li>`$L_1 := \{aba, bab, ab\}, L_2 := \{bb,ab,ba\}$`. Dann ist `$L_1 / L_2 = \{\varepsilon, a, b\}$` und `$L_1 \setminus L_2 = \{aba, bab\}$`<small><sup><a href="#ref3" name="anchor3">[3]</a></sup></small></li> <li>`$PKP \notin \cal NPC$`<small><sup><a href="#ref4" name="anchor4">[4]</a></sup></small></li> <li>Es kann sein, dass die Ableitung eines Wortes nicht eindeutig ist, aber der Syntaxbaum eindeutig ist.</li> <li>F&uuml;r jedes Wort w gibt es einen DEA, der w akzeptiert<small><sup><a href="#ref5" name="anchor5">[5]</a></sup></small></li> <li>`$L' \alpha L$` bedeutet, dass L' polynomial transformierbar in L ist.</li> <li>`$L' \alpha_T L$` bedeutet, dass L' Turing-reduzierbar in L ist.</li> </ul> <h2>Termin</h2> <p><strong>Datum</strong>: Mittwoch, der 22.02.2012 um 14:00 Uhr (siehe <a href="http://i11www.iti.uni-karlsruhe.de/teaching/winter2011/tgi/index">Vorlesungswebsite</a>) <strong>Ort</strong>: Steht <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/anmeldung.pdf">hier</a>. Ich schreibe im Tulla, manche noch im Gaede und andere im HS a. F., Daimler oder Benz. Laut dieser Liste schreiben 295 Personen diese Klausur! <strong>Dauer</strong>: 120 min. (siehe <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/tgi1112-t1.pdf">erste Folie</a>) <strong>Punkte</strong>: Bisher waren es meist ca. 60, von denen man 20 zum Bestehen benötigt hat. <strong>Übungsschein</strong>: <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/scheine.pdf">Liste</a> der 195 Leute, die ihn bestanden haben. Der Übungsschein bringt einen Klausurbonus. Allerdings habe ich keine Ahnung, wie hoch dieser ist. edit: +0,3 zur Klausurnot (Danke Alexander ☺ )</p> <p>Ach ja, ich habe “<a href="http://info.php-4.info/attachment.php?attachmentid=260&amp;sid=dcc186e19164016b828792ff3c04a046">Yet Another Info 3 Resume</a>” noch gar nicht verlinkt. Das ist sehr kurz und hat viele wichtige Informationen.</p> <h2>Klausurergebnisse</h2> <p>Die Klausurergebnisse sind nun <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/notenhk.pdf">öffentlich</a>. Die Liste scheint nach Matrikelnummer sortiert zu sein … tolle Anonymisierung, da wir ja auch im Saal nach Matrikelnummern sortiert waren. Und falls irgendjemand es vergessen hat: Hier ist die <a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/anmeldung.pdf">öffentliche Liste der Matrikelnummern</a>. Tja, so werden wir verschaukelt was den Datenschutz angeht.</p> <p>edit: Das Leck scheint ausgebessert worden zu sein. Nun sind die Noten nach Klausur-ID sortiert. Sehr schön ☺</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/02/tgi-notenverteilung-300x257.png"><img src="../images/2012/02/tgi-notenverteilung-300x257.png" alt="Notenverteilung der TGI Klausur im WS 2011/2012 am KIT" width="" height="" class="size-medium wp-image-18881" /></a><p class="wp-caption-text">Notenverteilung der TGI Klausur im WS 2011/2012 am KIT</p></div> <h2>Einzelnachweise</h2> <ol> <li><a name="ref1" href="#anchor1">↑</a>: 2. Klausur WS 2003/2004, Aufgabe 1a</li> <li><a name="ref2" href="#anchor2">↑</a>: 1. Klausur WS 2003/2004, Aufgabe 5</li> <li><a name="ref3" href="#anchor3">↑</a>: 1. Klausur WS 2007/2008, Aufgabe 3c</li> <li><a name="ref4" href="#anchor4">↑</a>: 1. Klausur WS 2007/2008, Aufgabe 5</li> <li><a name="ref5" href="#anchor5">↑</a>: 1. Klausur WS 2010/2011, Aufgabe 5</li> </ol> Kellerautomat //martin-thoma.com/kellerautomat/ Fri, 17 Feb 2012 20:17:01 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/kellerautomat <p>Ein Kellerautomat ist ein Endlicher Automat mit einem Stack (“Kellerspeicher”). Er wird mit PDA (pushdown automaton) bzw. NPDA (nondeterministic pushdown automaton) abgekürzt.</p> <p>Laut Wikipedia verwendet die Gleitkommaeinheit einen PDA. Dazu habe ich allerdings keine Quelle, das ist also mit Vorsicht zu genießen.</p> <p>Ein weiterer Einsatzzweck ist die Syntaxanalyse einer Tokenfolge. Das kann für Compiler oder Interpreter von Interesse sein.</p> <h2>Definitionen</h2> <p>Der <strong>Kellerautomat</strong> ist als 7-Tupel definiert:</p> <p><code>$(Q, \Sigma, \Gamma, q_0, Z_0, \delta, F)$</code>, wobei</p> <ul> <li>Q: endliche Zustandsmenge</li> <li>`$\Sigma$`: endliches Eingabealphabet</li> <li>`$\Gamma$`: endliches STACK-Alphabet</li> <li>`$q_0 \in Q$`: Anfangszustand</li> <li>`$Z_0 \in \Gamma$`: Initialisierung des STACK</li> <li>`$\delta: Q \times (\Sigma \cup \{\varepsilon\}) \times \Gamma \rightarrow 2^{Q \times \Gamma^*}$`.</li> <li>`$F \subseteq Q$`: Menge der akzeptierenden Endzust&auml;nde.</li> </ul> <p>Bemerkenswert ist hierbei, dass F leer sein kann. Dies ist möglich, da ein PDA auch durch leeren Stack akzeptieren kann.</p> <p>Die Zustandsüberführungsfunktion ist etwas umständlich beschrieben. Dort steht, dass jede Regel folgende Form hat: <code>$\delta(\text{Zustand}, \text{Eingabesymbol}, \text{Stacksymbol}) = (\text{Neuer Zustand}, \text{Neuer Stack})$</code></p> <p>Die <strong>Konfiguration eines PDA</strong> ist ein Tripel <code>$(q, w, \alpha)$</code>, wobei</p> <ul> <li>`$q \in Q$`: aktueller Zustand</li> <li>`$w \in \Sigma^*$`: der Teil der Eingabe, der noch nicht gelesen wurde</li> <li>`$\alpha \in \Gamma^*$`: der STACK-Inhalt</li> </ul> <p>Ein PDA ist <strong>deterministisch</strong> <code>$: \Leftrightarrow |\delta(q, a, Z)| + |\delta(q, \varepsilon, Z)| \leq 1 ~~~ \forall_{q \in Q, a \in \Sigma, Z \in \Gamma}$</code>.</p> <h2>Anschaulich</h2> <p>Du hast einen Kartenstapel (deine Eingabe, auf der du immer nur ein Zeichen lesen darfst), einen Stapel für Notizzettel, wobei am Anfang nur ein Notizzettel dort liegt und immer nur ein Symbol auf dem Zettel steht (dein Stack, der mit <code>$Z_0 \in \Gamma$</code> initialisiert ist), einen Zustand und eine Menge Regeln (<code>$\delta$</code>).</p> <p>Nun schaust du dir in jedem Schritt die oberste Karte auf dem Kartenstapel an und legst sie weg. Des Weiteren schaust du dir deine oberste Notiz an und legst sie weg und überprüfst deinen Zustand. Aus diesen Informationen schlussfolgerst du, was du als nächstes machst. Du kannst dir aussuchen in welchen Zustand du gehen willst und was du noch auf deinen Notiz-Stapel tun willst. Du kannst auch einfach nichts auf den Notiz-Stapel legen.</p> <h2>Beispiele</h2> <p>Sei <code>$L = \{w \in \{0,1,2\}^* | w = 0^i1^j2^j ~~~ i, j \in \mathbb{N}\}$</code></p> <p><code>$(\{q_0, q_1, q_2\}, \{0, 1, 2\}, \{1, \#\}, q_0, \#, \delta, \emptyset)$</code> mit</p> <p><code>$\delta(q_0, 0, \#) = \{(q_0, \#), (q_1, \#)\}, $</code> <code>$\delta(q_1, 1, \#) = \{(q_1, 1)\}, $</code> <code>$\delta(q_1, 1, 1) = \{(q_1, 11)\}, $</code> <code>$\delta(q_1, 2, 1) = \{(q_2, \varepsilon)\}, $</code> <code>$\delta(p, a, Z) = \emptyset $</code> sonst.</p> <p>Der Kellerautomat akzeptiert durch leeren STACK. Aus diesem Grund legen wir am Anfang auch immer wieder # auf den Stack. Sonst würde der PDA zu früh akzeptieren.</p> <p>Da <code>$|\delta(q_0, 0, \#) = 2 &gt; 1|$</code> ist dieser Kellerautomat Nicht-Deterministisch.</p> <h2>Umformungen</h2> <h3>Akzeptierender Endzustand &rarr; leerer STACK</h3> <p>Siehe Skript von Prof. Dr. Dorothea Wagner, S. 107.</p> <p>Gegeben sei ein Kellerautomat <code>${\cal K}_1 (Q_1, \Sigma, \Gamma_1, \delta_1, q_0^1, Z_0^1, F_1)$</code> der durch akzeptierenden Endzustand akzeptiert. Wir wollen einen neuen Automaten <code>${\cal K}_2 (Q_2, \Sigma, \Gamma_2, \delta_2, q_0^2, Z_0^2, F_2)$</code> der durch leeren STACK akzeptiert.</p> <p><strong>Idee</strong>: Wir führen einen neuen Zustand <code>$q_E$</code> ein, bei dessen Erreichen wir den STACK leeren. Um zu verhindern, dass der STACK zwischenzeitlich leer wird, legen wir zu beginn das STACK-Symbol <code>$Z_0^2$</code> ab.</p> <p><strong>Formal</strong>: <code>$Q_2 := Q_1 \cup \{q_0^2, q_E\}$</code>, wobei <code>$q_0^2$</code> der neue Anfangszustand von <code>${\cal K}_2$</code> ist. <code>$\Gamma_2 := \Gamma_1 \cup \{Z_0^2\}$</code>, wobei <code>$Z_0^2$</code> den STACK initialisiert.</p> <p>Die Menge <code>$\delta_2(q, a, Z)$</code> für <code>$a \in \Sigma \cup \{\varepsilon\}$</code> und <code>$Z \in \Gamma_2$</code> sei durch folgende Bedingungen festgelegt:</p> <p>Sorge für die gleiche Anfangssituation: <code>$\delta_2(q_0^2, \varepsilon, Z_0^2) = \{(q_0^1, Z_0^1Z_0^2)\}$</code></p> <p>Falls der Zustand, das gelesene Zeichen und das STACK-Symbol im “alten” Automaten sind, dann wie gehabt: <code>$\delta_2(q, a, Z) = \delta_1(q, a, Z) \text{f&amp;uuml;r } (q \in Q_1, a \neq \varepsilon, Z \in \Gamma_1) \lor (q \in Q_1 \setminus F_1, a = \varepsilon, Z \in \Gamma_1)$</code></p> <p>Sorge dafür, dass die STACK-Leerungsregel aufgerufen wird, falls der Zustand akzeptierend ist: <code>$\delta_2(q, \varepsilon, Z) = \delta_1(q, \varepsilon, Z) \cup \{(q_E, \varepsilon)\} \text{f&amp;uuml;r } q \in F_1, Z \in \Gamma_2$</code></p> <p>Diese Regel leert den STACK: <code>$\delta_2(q_E, \varepsilon, Z) = \{(q_E, \varepsilon)\} \text{ f&amp;uuml;r } Z \in \Gamma_2$</code></p> <h3>Leerer STACK &rarr; akzeptierender Endzustand</h3> <p>Siehe Skript von Prof. Dr. Dorothea Wagner, S. 107.</p> <p>Gegeben sei ein Kellerautomat <code>${\cal K}_1 (Q_1, \Sigma, \Gamma_1, \delta_1, q_0^1, Z_0^1, F_1)$</code> der durch leeren STACK akzeptiert. Wir wollen einen neuen Automaten <code>${\cal K}_2 (Q_2, \Sigma, \Gamma_2, \delta_2, q_0^2, Z_0^2, F_2)$</code> der durch akzeptierenden Endzustand akzeptiert.</p> <p><strong>Idee</strong>: Wir legen ein zusätzliches Symbol <code>$Z_0^2$</code> auf den STACK. Wird <code>$Z_0^2$</code> gelesen, ist der STACK noch nicht leer, aber man kann in einen akzeptierenden Zustand <code>$q_F$</code> wechseln.</p> <p><strong>Formal</strong>: <code>$Q_2 := Q_1 \cup \{q_0^2, q_F\}$</code>, wobei <code>$q_0^2$</code> Anfangszustand von <code>${\cal K}_2$</code> ist und <code>$F_2 := \{q_F\}$</code> <code>$\Gamma_2 := \Gamma_1 \cup \{Z_0^2\}$</code>, wobei <code>$Z_0^2$</code> Initialisierung des STACKS von <code>${\cal K}_2$</code> ist und <code>$\delta_2$</code> festgelegt durch:</p> <p>Zuerst sorgen wir dafür, dass <code>$Z_0^2$</code> ganz unten im STACK ist: <code>$\delta_2(q_0^2, a, X) = \begin{cases} \{q_0^1, Z_0^1, Z_0^2\} &amp; \text{falls } a= \varepsilon \text{ und } X = Z_0^2\\ \emptyset &amp; \text{sonst} \end{cases}$</code></p> <p>Dann wie gehabt: <code>$\delta_2(q, a, Z) = \delta_1(q, a, Z) \text{, falls } q \in Q_1, a \in \Sigma \cup \{\varepsilon\} \text{ und } Z \in \Gamma_1$</code></p> <p>Und am Schluss auch akzeptieren: <code>$\delta_2(q, \varepsilon, Z_0^2) = \{(q_F, \varepsilon)\} \text{ f&amp;uuml;r } q \in Q_1$</code>.</p> <h2>Dies und das</h2> <ul> <li>Ein Kellerautomat mit zwei STACKs ist Turingm&auml;chtig. (&rarr; <a href="http://de.wikipedia.org/wiki/Zweikellerautomat" title="Zweikellerautomat">Zweikellerautomat</a>)</li> <li>Ein NPDA erkennt genau die kontextfreien Sprachen.</li> <li>Ein PDA erkennt manche kontextfreie Sprachen, aber nicht alle. (Genauer: <a href="http://de.wikipedia.org/wiki/Deterministisch_kontextfreie_Sprache">Deterministisch kontextfreie Sprache</a>)</li> <li>Zu jedem PDA, der eine Sprache L durch einen akzeptierenden Endzustand akzeptiert, kann ein PDA konstruiert werden, der L mit leerem STACK akzeptiert (und umgekehrt).</li> <li>F&uuml;r jede Grammatik G in Greibach-Normalform gibt es einen PDA.</li> </ul> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Kellerautomat">Kellerautomat</a></li> <li><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/tgi_skript_ws11.pdf">Theoretische Grundlagen der Informatik</a>: Skript von Prof. Dr. Dorothea Wagner, ab S. 105</li> <li><a href="../sprachen-automaten-und-grammatiken/" title="Sprachen, Automaten und Grammatiken: Ein &Uuml;berblick">Sprachen, Automaten und Grammatiken: Ein &Uuml;berblick</a></li> </ul> Komplexitätsklassen in der Informatik: Ein Überblick //martin-thoma.com/komplexitatsklassen-in-der-informatik-ein-uberblick/ Thu, 16 Feb 2012 15:51:04 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/komplexitatsklassen-in-der-informatik-ein-uberblick <p>Komplexitätsklassen werden in der Theoretischen Informatik verwendet um den Ressourcenbedarf von Algorithmen bzw. Problemen einzuordnen. Meist betrachtet man die Laufzeit- und die Speicherplatzkomplexität, aber es wäre prinzipiell auf Vorstellbar, dass man andere Kriterien nutzt. Ich werde in diesem Artikel mal kurz die in der Vorlesung behandelten Klassen vorstellen.</p> <p>Da es umständlich ist, werde ich im Folgenden nur noch von Problemen reden. Gemeint sind aber meist auch formale Sprachen und Algorithmen.</p> <h2>Die Klasse P</h2> <p>In der Klasse <code>$\cal P$</code> sind alle Probleme, die mit einer deterministischen Turingmaschine in polynomialzeit lösbar sind. Das sind also alle Probleme, für die es einen Algorithmus gibt, der in <code>$\cal O(n^i), i \in \mathbb{N}_0$</code> ist.</p> <p>Wenn es allerdings <em>noch</em> keinen Algorithmus gibt, der ein Problem in polynomialzeit löst, kann das Problem dennoch in <code>$\cal P$</code> liegen. Dann muss es einen besseren Algorithmus zur Lösung des Problems geben.</p> <h2>Die Klasse NP</h2> <p>In der Klasse <code>$\cal NP$</code> sind alle Probleme, die mit einer <strong>nicht-deterministischen</strong> Turingmaschine in polynomialzeit lösbar sind. Das besondere an einer nicht-determinisitschen Turingmaschine ist das Orakelmodul. Es liefert einfach die Lösung. Wie es das macht, wissen wir nicht. Irgendwie geht es halt. Diese Lösung muss in polynomialzeit von einer deterministischen Turingmaschine verifiziert werden.</p> <p>Was liegt dann nicht in <code>$\cal NP$</code>? Das Orakelmodul hört sich so mächtig an, dass eventuell alle Probleme in <code>$\cal NP$</code> liegen könnten. Weit gefehlt. Suchprobleme liegen häufig (aber nicht immer) außerhalb von <code>$\cal NP$</code>. Das sind dann Probleme mit einer Fragestellung à la “Gib eine optimale Tour durch eine gegebene Menge an Städten an”. Wenn das Orakel-Modul eine solche Tour liefert, muss der deterministische Teil noch schauen, ob es eventuell eine längere Tour gibt.</p> <p>Die wohl berühmteste Fragestellung der Theoretischen Informatik lautet nun:</p> <p><strong>P vs. NP</strong>: Gibt es Probleme, die in NP liegen, aber nicht in P?</p> <p>Es ist wohl anschaulich klar, dass gilt: <code>$\cal P \subset NP$</code>. P vs. NP ist die Frage, ob <code>$\cal P = NP$</code> oder <code>$\cal P \subsetneq NP$</code>. Oder nochmals anders formuliert: <code>$\cal NP \setminus P \stackrel{?}{=} \emptyset$</code></p> <h3>Die Klasse NPC</h3> <p>Die Klasse der NP-Vollständigen Probleme ist echt in NP, also <code>$\cal NPC \subsetneq NP$</code>. Das besondere an <code>$\cal NPC$</code> ist, dass jedes Probleminstanz in <code>$\cal NP$</code> in eine Instanz eines beliebigen Problems in <code>$\cal NPC$</code> umgewandelt werden kann.</p> <p>Das es ein solches Problem gibt, hat Cook 1971 mit <a href="http://de.wikipedia.org/wiki/Erf%C3%BCllbarkeitsproblem_der_Aussagenlogik">SAT</a> gezeigt. Cook hat also anschaulich folgendes gemacht:</p> <div style="width: 397px" class="wp-caption aligncenter"><a href="../images/2012/02/npc-sat.png"><img src="../images/2012/02/npc-sat.png" alt="SAT ist in NPC" width="" height="" class="size-full wp-image-15231" /></a><p class="wp-caption-text">SAT ist in NPC</p></div> <p>Für alle folgenden Beweise, dass ein Problem in <code>$\cal NPC$</code> liegt, wurde der Satz von Cook verwendet. Laut diesem Satz (dessen Beweis wahnsinning lang ist) lässt sich jede Probleminstanz von Problemen in <code>$\cal NP$</code> sich in eine Instanz von SAT umwandeln. Es reicht also zu zeigen, dass sich eine beliebige SAT-Instanz I in eine Instanz I’ des neuen Problems in polynomialzeit umwandeln lässt. Diese beiden Instzanzen müssen in folgender Beziehung stehen: Für I existiert eine Lösung <code>$\Leftrightarrow$</code> für I’ existiert eine Lösung:</p> <div style="width: 470px" class="wp-caption aligncenter"><a href="../images/2012/02/proof-new-npc.png"><img src="../images/2012/02/proof-new-npc.png" alt="Beweis, dass 3-SAT in NPC liegt" width="" height="" class="size-full wp-image-15241" /></a><p class="wp-caption-text">Beweis, dass 3-SAT in NPC liegt</p></div> <p>Sobald man von einem Problem sicher weiß, dass es in <code>$\cal NPC$</code> liegt, kann man natürlich auch etwas anderes als SAT verwenden.</p> <p>Im Bezug auf P vs. NP ist es vor allem interessant. Wenn ein Problem nicht in P, aber in NP liegt, dann ist sicher jedes Problem in NPC außerhalb von P. Also: <code>$\cal P \neq NP \Rightarrow P \cap NPC = \emptyset$</code>. Warum? Angenommen es existiert ein Problem P für das gilt:</p> <ul> <li>`$P \in \cal NP$`</li> <li>`$P \notin \cal P$`</li> <li>`$P \notin \cal NPC$`</li> </ul> <p>Dann gibt es eine polynomielle Transformation von jeder Instanz von P in eine Probleminstanz von einem beliebigem Problem in <code>$\cal NPC$</code>. Damit kann jedes Problem in <code>$\cal NPC$</code> nicht mehr in <code>$\cal P$</code> liegen, da sonst auch <code>$P \in \cal P$</code>.</p> <h2>NPI, co-P und co-NP</h2> <p>Formal gilt: <code>$\cal NPI := NP \setminus (P \cup NPC)$</code>. Es sind also alle Probleme, die innerhalb von <code>$\cal NP$</code> sind, aber außerhalb von <code>$\cal P$</code> und noch nicht in <code>$\cal NPC$</code> in <code>$\cal NPI$</code>. Es ist also so eine Art “Zwischenklasse”.</p> <p>Um es etwas anschaulicher zu machen, habe ich mal folgendes Bildchen erstellt:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/02/PvsNP.png"><img src="../images/2012/02/PvsNP.png" alt="P vs. NP: Die Klassen P, NP, NPC und NPI im &Uuml;berblick" width="" height="" class="size-full wp-image-14511" /></a><p class="wp-caption-text">P vs. NP: Die Klassen P, NP, NPC und NPI im &Uuml;berblick</p></div> <p>Bemerkenswert ist folgende Aussage: Im Fall <code>$\cal P = NP$</code> ist auch <code>${\cal P} \setminus \{\emptyset, \Sigma^*\} = {\cal NPC}$</code> (siehe Nachklausur von 2007 / 2008, Frage 5). Warum stimmt das? Damit ein Problem <code>$\in \cal NPC$</code> ist, muss es nur eine polynomielle Transformation von jedem Problem in NP auf das eine Problem geben. Das ist offensichtlich der Fall, wenn man alle Probleme in NP in polynomieller Zeit lösen kann. In diesem Fall kann man das Entscheidungsproblem lösen und eine Ja-Instanz auf eine beliebige andere Ja-Instanz abbilden und analog Nein-Instanzen auf Nein-Instanzen abbilden. Da <code>$\emptyset$</code> keine Ja-Instanz hat und <code>$\Sigma$</code> keine Nein-Instanz hat, muss man diese herausnehmen.</p> <p>Formal gilt: <code>$\text{co-}{\cal P} := \{L \in \Sigma^* | L^C \in {\cal P}\}$</code> und analog <code>$\text{co-}{\cal NP} := \{L \in \Sigma^* | L^C \in {\cal NP}\}$</code>.</p> <p>Folgende Aussage finde ich dazu sehr interessant: <code>$L \in {\cal NPC} \land L \in \text{co-}{\cal NP} \Rightarrow {\cal NP} = \text{co-}{\cal NP}$</code></p> <h2>D-TAPE und N-TAPE</h2> <p>Im Skript wurde das seltsam geschrieben (<code>$\cal DTAPE$</code>). Ich habe so nicht mehr erkannt, dass es TAPE heißen soll. In der Klausur sollte man sich davon nicht irritieren lassen.</p> <p>Formal: <code>$D-TAPE(s(n)) := \{L | \text{Es existiert eine determinitistische TM, die L mit Platzbedarf s(n) akzeptiert.}\}$</code> <code>$N-TAPE(s(n)) := \{L | \text{Es existiert eine nicht-determinitistische TM, die L mit Platzbedarf s(n) akzeptiert.}\}$</code></p> <h2>Quellen und Material</h2> <ul> <li><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/tgi_skript_ws11.pdf">Theoretische Grundlagen der Informatik</a>: Skript von Prof. Dr. Dorothea Wagner</li> <li>Die Bilder stehen hier zur Verf&uuml;gung: <a href="../images/2012/02/komplexitaetsklassen-material.zip">Material zu den Komplexit&auml;tsklassen</a></li> </ul> Konstruktion der Chomsky-Normalform //martin-thoma.com/konstruktion-der-chomsky-normalform/ Sat, 11 Feb 2012 17:25:36 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/konstruktion-der-chomsky-normalform <div class="warning">Dieser Artikel k&ouml;nnte inhaltliche Fehler beinhalten. Bitte lest euch die Kommentare durch.</div> <p>Die Chomsky-Normalform ist eine bestimmte Art, eine kontextfreie Grammatik zu formulieren. Dabei haben nur die Produktionsregeln eine festgelegte Form, alles andere ist wie immer. Die Chomsky-Normalform kommt bei dem CYK-Algorithmus, der das Wortproblem für kontextfreie Grammatiken löst, zum Einsatz. Jede kontextfreie Grammatik kann in Chomsky-Normalform gebracht werden.</p> <h2>Die Chomsky-Normalform</h2> <p>Das Besondere an der Chomsky-Normalform ist, dass alle Regeln der Grammatik <code>$G (V, \Sigma, P, S)$</code> folgende Form haben: <code>$A \rightarrow BC$</code> oder <code>$A \rightarrow a$</code>. Dabei sind <code>$A, B, C \in V$</code> und <code>$a \in \Sigma$</code>.</p> <p>Falls die Grammatik in der Lage ist, das Leere Wort <code>$\varepsilon$</code> zu erzeugen, dann fügt man folgende Sonderregel hinzu: <code>$S' \rightarrow S | \varepsilon$</code>. Dabei darf S’ niemals auf der rechten Seite einer Produktion stehen.</p> <p>Eine Eigenschaft der Chomsky-Normalform ist, dass jedes Wort aus <code>$2 \cdot |w| - 1$</code> Ableitungen gebildet werden kann. (Falls das leere Wort gebildet werden kann sind es <code>$2 \cdot |w|$</code> Ableitungen für jedes nicht-leere Wort und eine Ableitung für das leere Wort) In jedem Ableitungsschritt erhält man entweder ein Terminal, oder ein weiteres Nicht-Terminal.</p> <h2>Konstruktion der CNF</h2> <p>Aus einer Grammatik <code>$G (V, \Sigma, P, S)$</code> kann mit folgenden vier Schritten eine Grammatik <code>$G' (V', \Sigma, P', S)$</code> in Chomsky-Normalform (CNF) erstellt werden:</p> <h3>Schritt 1</h3> <p>Immer wenn ein Symbol aus <code>$\Sigma$</code> in einer Produktion steht, wird dieses durch <code>$Y_a$</code> ersetzt und eine neue Produktion <code>$Y_a \rightarrow a$</code> zu P’ hinzugefügt.</p> <p>Es ist somit sichergestellt, dass alle Regeln entweder nur Nicht-Terminale auf der rechten Seite der Produktion stehen haben oder <code>$\varepsilon$</code> oder dass dort ein einzelnes Terminal steht.</p> <h3>Schritt 2</h3> <p>Immer wenn mehr als zwei Variablen auf der rechten Seite stehen, werden diese durch neue ersetzt. Sagen wir es stehen rechts m Variablen. Dann führt man m - 2 neue Variablen ein, fügt diese zu V’ hinzu, und macht aus einer Regel <code>$A \rightarrow B_1 B_2 ... B_m$</code> die Regeln <code>$A \rightarrow B_1 C_1, C_1 \rightarrow B_2 C_2, ..., C_{i+1} \rightarrow B_i C_i ... C_{m-2} \rightarrow B_{m-3} C_{m-3}$</code>.</p> <p>An dieser Stelle ist sichergestellt, dass alle Regeln entweder nur ein oder zwei Nicht-Terminale auf der rechten Seite der Produktion stehen haben oder <code>$\varepsilon$</code> oder dass dort ein einzelnes Terminal steht.</p> <h3>Schritt 3</h3> <p>Nun wollen wir alle <code>$\varepsilon$</code>-Übergänge entfernen.</p> <p>Um dies zu erreichen, suchen wir alle Regeln, die nach <code>$\varepsilon$</code> abbilden, also von der Form <code>$A \rightarrow \varepsilon$</code> sind. Dabei streichen wir die Regeln <code>$A \rightarrow \varepsilon$</code>. Falls A nun nicht mehr auf der linken Seite auftaucht, streichen wir es überall aus der rechten Seite. Falls dabei eine Regel zu <code>$B \rightarrow \varepsilon$</code> wird, streichen wir auch diese. Das wiederholen wir so lange, bis keine <code>$\varepsilon$</code>-Übergänge mehr vorhanden sind. Am Ende fügen wir die Regel <code>$S' \rightarrow S | \varepsilon$</code> hinzu, falls die Grammatik auf das leere Wort abbilden konnte.</p> <p>Nun ist sichergestellt, dass alle Regeln entweder nur ein oder zwei Nicht-Terminale auf der rechten Seite der Produktion stehen haben oder dass dort ein einzelnes Terminal steht. Allerdings kann es noch Kreise in der Ableitung geben, die man entfernen kann.</p> <h3>Schritt 4</h3> <p>In diesem Schritt entfernen wir eventuell vorhandene Kettenregeln, also Regeln der Form <code>$A_1 \rightarrow A_2 \rightarrow A_3 \rightarrow A_u \rightarrow A_1$</code>. Diese findet man mit einer Tiefensuche. Dann ersetzt man alle <code>$A_2, ..., A_u$</code> durch <code>$A_1$</code>. Die Regel <code>$A_1 \rightarrow A_1$</code> kann entfernt werden, da sie ja nichts ändert.</p> <h2>Beispiele</h2> <h3>Die Sprache der Palindrome</h3> <p>Gegeben sei folgende Grammatik: <code>$G(\underbrace{\{S\}}_{V}, \underbrace{\{a,b\}}_{\Sigma}, S, P)$</code> mit <code>$P = \{S \rightarrow \varepsilon | a | b | aSa | bSb \}$</code>.</p> <h4>Schritt 1</h4> <p><code>$S \rightarrow \varepsilon | Y_a | Y_b | Y_aSY_a | Y_bSY_b$</code> <code>$Y_a \rightarrow a$</code> <code>$Y_b \rightarrow b$</code></p> <h4>Schritt 2</h4> <p><code>$S \rightarrow \varepsilon | Y_a | Y_b | Y_aC_1 | Y_bC_2$</code> <code>$C_1 \rightarrow SY_a$</code> <code>$C_2 \rightarrow SY_b$</code> <code>$Y_a \rightarrow a$</code> <code>$Y_b \rightarrow b$</code></p> <h4>Schritt 3</h4> <p><code>$S \rightarrow Y_a | Y_b | Y_aC_1 | Y_bC_2$</code> <code>$C_1 \rightarrow SY_a$</code> <code>$C_2 \rightarrow SY_b$</code> <code>$Y_a \rightarrow a$</code> <code>$Y_b \rightarrow b$</code> <code>$S' \rightarrow S | \varepsilon$</code></p> <h4>Schritt 4</h4> <p>Keine Kettenregel vorhanden.</p> <h4>Ergebnis</h4> <p>Nun werden noch einzelne Nicht-Terminale durch die möglichen Terminale ersetzt und man ist fertig.</p> <p>Damit ist die Grammatik: <code>$G_{CNF} (\{S, S', Y_a, Y_b, C_1, C_2\}, \{a,b\}, S', P'))$</code> mit folgenden Produktionen P’: <code>$P' = \{S \rightarrow a | b | Y_aC_1 | Y_bC_2,$</code> <code>$~ C_1 \rightarrow SY_a,$</code> <code>$~ C_2 \rightarrow SY_b,$</code> <code>$~ Y_a \rightarrow a,$</code> <code>$~ Y_b \rightarrow b,$</code> <code>$~ S' \rightarrow S | \varepsilon\}$</code></p> <p>Sie ist also nicht schöner oder einfacher geworden, hat aber eine bestimmte Struktur erhalten.</p> <h2>Weiterf&uuml;hrende Links und Quellen</h2> <ul> <li><a href="http://de.wikipedia.org/wiki/Chomsky-Normalform">Wikipedia</a></li> <li>Uwe Sch&ouml;ning: <i>Theoretische Informatik- kurz gefasst</i>. 5.&nbsp;Auflage. Spektrum Akademischer Verlag, Heidelberg <span style="white-space:nowrap;">2008</span>, ISBN 978-3-8274-1824-1, S.&nbsp;44, <span class="plainlinks-print"><a rel="nofollow" class="external text" href="http://d-nb.info/986529222">DNB 986529222</a></span>.</li> <li>KIT: <ul> <li><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/tgi_skript_ws11.pdf">Skript</a> von Prof. Dr. Dorothea Wagner, S. 98</li> <li><a href="http://i11www.iti.uni-karlsruhe.de/_media/teaching/winter2011/tgi/uebung7.pdf">&Uuml;bung</a> vom 02.02.2012 - Hier ist ein sehr gutes, detailliertes Beispiel! </li> </ul></li> </ul> Minimierung eines Automaten mittels Äquivalenzklassenkonstruktion //martin-thoma.com/minimierung-eines-automaten-mittels-aquivalenzklassenkonstruktion/ Fri, 10 Feb 2012 22:18:38 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/minimierung-eines-automaten-mittels-aquivalenzklassenkonstruktion <p>Wenn ein Endlicher Automat gegeben ist, kann durch die Konstruktion von Äquivalenzklassen sehr einfach ein Automat mit gleichem Akzeptanzverhalten und minimaler Anzahl an Zuständen gefunden werden. Dafür benötigt man im Wesentlichen sogar nur drei Schritte.</p> <h2>Der Algorithmus</h2> <ol> <li><strong>&Uuml;berfl&uuml;ssige Zust&auml;nde streichen</strong>: Manche Zust&auml;nde sind nicht erreichbar. Diese k&ouml;nnen offensichtlich gestrichen werden.</li> <li><strong>Akzeptierende von nichtakzeptierenden Zust&auml;nden trennen</strong>: Alle akzeptierenden Zust&auml;nde werden in eine &Auml;quivalenzklasse gepackt, alle Zust&auml;nde die nicht akzeptieren kommen in eine andere Klasse.</li> <li><strong>Zust&auml;nde trennen</strong>: F&uuml;r jedes Zeichen des Eingabealphabets `$\Sigma$` schreibt man sich auf, in welchen Zustand der Zustand f&uuml;hrt. Wenn zwei Zust&auml;nde in verschiedene Klassen f&uuml;hren, werden diese getrennt. Dies wiederholt man so lange, bis man ein mal alle Zeichen aus `$\Sigma$` durchgegangen ist, ohne dass Zust&auml;nde getrennt wurden.</li> </ol> <h2>Beispiel</h2> <p>Gegeben sei folgender Endlicher Automat A: <code>$A = (\{0,1\}, \{S, A, B, C, D, E, F, G, H, I\}, S, \sigma, \{D\})$</code> mit folgender Übergangsfunktion <code>$\sigma$</code>:</p> <div style="width: 402px" class="wp-caption aligncenter"><a href="../images/2012/02/endlicher-automat-gross.png"><img src="../images/2012/02/endlicher-automat-gross.png" alt="Endlicher Automat mit &uuml;berfl&uuml;ssigen Zust&auml;nden" width="" height="" class="size-full wp-image-13451" /></a><p class="wp-caption-text">Endlicher Automat mit &uuml;berfl&uuml;ssigen Zust&auml;nden</p></div> <p>Es ist offensichtlich, dass I nicht erreicht werden kann. Da der Graph gerichtet ist, kann man schnell sehen, dass auch H und G nicht erreicht werden können. Algorithmisch kann man diese Zustände durch eine Tiefensuche bestimmen.</p> <p>Nach Schritt 1 haben wir also den Automaten <code>$A_1 = (\{0,1\}, \{S, A, B, C, D, E, F\}, S, \sigma, \{D\})$</code>:</p> <div style="width: 350px" class="wp-caption aligncenter"><a href="../images/2012/02/endlicher-automat-kleiner.png"><img src="../images/2012/02/endlicher-automat-kleiner.png" alt="Keine &uuml;berfl&uuml;ssen Zust&auml;nde im Endlichen Automaten" width="" height="" class="size-full wp-image-13471" /></a><p class="wp-caption-text">Keine &uuml;berfl&uuml;ssen Zust&auml;nde im Endlichen Automaten</p></div> <p>In Schritt 2 erstellen wir also zuerst eine Äquivalenzklasse der Zustände: <code>$\{S, A, B, C, D, E, F\}$</code>.</p> <p>Die akzeptierenden Zustände werden von den nicht akzeptierenden getrennt: <code>$\{D\}, \{S, A, B, C, E, F\}$</code></p> <p>In Schritt 3 gehen wir nun immer wieder die Zeichen “0” und “1” aus <code>$\Sigma$</code> durch: In welche Klassen führt “0”? <a href="../images/2012/02/aequivalenzklassen-1.png"><img src="../images/2012/02/aequivalenzklassen-1.png" alt="&Auml;quivalenzklassen - Schritt 1" title="&Auml;quivalenzklassen - Schritt 1" width="220" height="71" class="aligncenter size-full wp-image-13631" /></a></p> <p>C wird also von <code>$\{S, A, B, E, F\}$</code> getrennt. Wir haben folgende Klassen: <code>$\{C\}, \{D\}, \{S, A, B, E, F\}$</code></p> <p>“1” trennt nun “A” von <code>$\{S, B, E, F\}$</code>: <a href="../images/2012/02/aequivalenzklasse-2.png"><img src="../images/2012/02/aequivalenzklasse-2.png" alt="&Auml;quivalenzklassen - Schritt 2" title="&Auml;quivalenzklassen - Schritt 2" width="246" height="66" class="aligncenter size-full wp-image-13661" /></a></p> <p>“0” trennt nun “S” von <code>$\{B, E, F\}$</code>: <a href="../images/2012/02/aequivalenzklasse-3.png"><img src="../images/2012/02/aequivalenzklasse-3.png" alt="&Auml;quivalenzklassen - Schritt 3" title="&Auml;quivalenzklassen - Schritt 3" width="267" height="65" class="aligncenter size-full wp-image-13681" /></a></p> <p>Wir haben nun die Äquivalenzklassen <code>$\{S\}, \{A\}, \{C\}, \{D\}, \{B, E, F\}$</code>.</p> <p>Im nächsten Schritt sehen wir, dass “1” nicht mehr trennt und “0” auch nicht nochmals etwas trennt. Wir sind also fertig. Die Zustände B, E und F können zu einem zusammengefasst werden. Ich nenne ihn mal T (für Trash, da man in diesem Zustand niemals mehr akzeptieren kann). Damit ist unser minimaler Endlicher Automat folgender:</p> <p><a href="../images/2012/02/endlicher-automat-minimal.png"><img src="../images/2012/02/endlicher-automat-minimal.png" alt="Minimaler Endlicher Automat" title="Minimaler Endlicher Automat" width="346" height="278" class="aligncenter size-full wp-image-13711" /></a></p> <h2>LaTeX</h2> <p>Das ist der LaTeX-Code für die Automaten:</p> <div class="highlight"><pre><code class="language-python" data-lang="python">\<span class="n">documentclass</span><span class="p">{</span><span class="n">scrartcl</span><span class="p">}</span> \<span class="n">usepackage</span><span class="p">{</span><span class="n">amsmath</span><span class="p">}</span> \<span class="n">usepackage</span><span class="p">{</span><span class="n">tikz</span><span class="p">}</span> \<span class="n">usepackage</span><span class="p">{</span><span class="n">pst</span><span class="o">-</span><span class="n">node</span><span class="p">}</span> \<span class="n">usetikzlibrary</span><span class="p">{</span><span class="n">arrows</span><span class="p">,</span><span class="n">automata</span><span class="p">}</span> \<span class="n">begin</span><span class="p">{</span><span class="n">document</span><span class="p">}</span> \<span class="n">begin</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}[</span><span class="o">&gt;=</span><span class="n">stealth</span><span class="s">&#39;,shorten &gt;=1pt,auto,node distance=2cm]</span> \<span class="n">node</span><span class="p">[</span><span class="n">initial</span><span class="p">,</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="p">{</span><span class="sb">`$S$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">,</span> <span class="n">left</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$A$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$B$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">,</span> <span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$C$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">,</span><span class="n">accepting</span><span class="p">]</span> <span class="p">(</span><span class="n">D</span><span class="p">)</span> <span class="p">[</span><span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">,</span> <span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$D$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">E</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">C</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$E$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">F</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">B</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$F$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">G</span><span class="p">)</span> <span class="p">[</span><span class="n">left</span> <span class="n">of</span><span class="o">=</span><span class="n">B</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$G$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">H</span><span class="p">)</span> <span class="p">[</span><span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$H$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">I</span><span class="p">)</span> <span class="p">[</span><span class="n">left</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$I$`</span><span class="p">};</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">A</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">B</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">C</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">F</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">D</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">E</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">D</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">S</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">E</span><span class="p">)</span> <span class="n">edge</span> <span class="p">[</span><span class="n">loop</span> <span class="n">right</span><span class="p">]</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">E</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">F</span><span class="p">)</span> <span class="n">edge</span> <span class="p">[</span><span class="n">loop</span> <span class="n">left</span><span class="p">]</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">F</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">G</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">B</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">G</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">F</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">H</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">S</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">I</span><span class="p">)</span> <span class="n">edge</span> <span class="p">[</span><span class="n">loop</span> <span class="n">above</span><span class="p">]</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">I</span><span class="p">);</span> \<span class="n">end</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}</span> <span class="n">Ueberfluessige</span> <span class="n">weg</span><span class="p">:</span> \<span class="n">begin</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}[</span><span class="o">&gt;=</span><span class="n">stealth</span><span class="s">&#39;,shorten &gt;=1pt,auto,node distance=2cm]</span> \<span class="n">node</span><span class="p">[</span><span class="n">initial</span><span class="p">,</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="p">{</span><span class="sb">`$S$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">,</span> <span class="n">left</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$A$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$B$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">,</span> <span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$C$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">,</span><span class="n">accepting</span><span class="p">]</span> <span class="p">(</span><span class="n">D</span><span class="p">)</span> <span class="p">[</span><span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">,</span> <span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$D$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">E</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">C</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$E$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">F</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">B</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$F$`</span><span class="p">};</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">A</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">B</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">C</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">F</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">D</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">E</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">D</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">S</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">E</span><span class="p">)</span> <span class="n">edge</span> <span class="p">[</span><span class="n">loop</span> <span class="n">right</span><span class="p">]</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">E</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">F</span><span class="p">)</span> <span class="n">edge</span> <span class="p">[</span><span class="n">loop</span> <span class="n">left</span><span class="p">]</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">F</span><span class="p">);</span> \<span class="n">end</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}</span> <span class="n">Minimal</span><span class="p">:</span> \<span class="n">begin</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}[</span><span class="o">&gt;=</span><span class="n">stealth</span><span class="s">&#39;,shorten &gt;=1pt,auto,node distance=2cm]</span> \<span class="n">node</span><span class="p">[</span><span class="n">initial</span><span class="p">,</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="p">{</span><span class="sb">`$S$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">,</span> <span class="n">left</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$A$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$T$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="p">[</span><span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">,</span> <span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$C$`</span><span class="p">};</span> \<span class="n">node</span><span class="p">[</span><span class="n">state</span><span class="p">,</span><span class="n">accepting</span><span class="p">]</span> <span class="p">(</span><span class="n">D</span><span class="p">)</span> <span class="p">[</span><span class="n">right</span> <span class="n">of</span><span class="o">=</span><span class="n">A</span><span class="p">,</span> <span class="n">below</span> <span class="n">of</span><span class="o">=</span><span class="n">S</span><span class="p">]</span> <span class="p">{</span><span class="sb">`$D$`</span><span class="p">};</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">S</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">A</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">B</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">A</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">C</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">B</span><span class="p">)</span> <span class="n">edge</span> <span class="p">[</span><span class="n">loop</span> <span class="n">left</span><span class="p">]</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">B</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">}</span> <span class="p">(</span><span class="n">D</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">C</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">B</span><span class="p">);</span> \<span class="n">path</span><span class="p">[</span><span class="o">-&gt;</span><span class="p">]</span> <span class="p">(</span><span class="n">D</span><span class="p">)</span> <span class="n">edge</span> <span class="n">node</span> <span class="p">{</span><span class="mi">0</span><span class="p">,</span><span class="mi">1</span><span class="p">}</span> <span class="p">(</span><span class="n">S</span><span class="p">);</span> \<span class="n">end</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}</span> \<span class="n">end</span><span class="p">{</span><span class="n">document</span><span class="p">}</span></code></pre></div> <p>Und hier die Bilder mit den Pfeilchen:</p> <div class="highlight"><pre><code class="language-python" data-lang="python">\<span class="n">documentclass</span><span class="p">{</span><span class="n">article</span><span class="p">}</span> \<span class="n">usepackage</span><span class="p">{</span><span class="n">amsmath</span><span class="p">}</span> \<span class="n">usepackage</span><span class="p">{</span><span class="n">tikz</span><span class="p">}</span> \<span class="n">usetikzlibrary</span><span class="p">{</span><span class="n">calc</span><span class="p">,</span><span class="n">shapes</span><span class="p">}</span> \<span class="n">newcommand</span><span class="p">{</span>\<span class="n">tikzmark</span><span class="p">}[</span><span class="mi">1</span><span class="p">]{</span>\<span class="n">tikz</span><span class="p">[</span><span class="n">overlay</span><span class="p">,</span><span class="n">remember</span> <span class="n">picture</span><span class="p">]</span> \<span class="n">node</span> <span class="p">(</span><span class="c">#1) {};}</span> \<span class="n">newcommand</span><span class="p">{</span>\<span class="n">DrawBoxi</span><span class="p">}[</span><span class="mi">5</span><span class="p">]{</span> \<span class="n">begin</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}[</span><span class="n">overlay</span><span class="p">,</span><span class="n">remember</span> <span class="n">picture</span><span class="p">,</span><span class="o">-</span><span class="n">latex</span><span class="p">,</span><span class="n">shorten</span> <span class="o">&gt;=</span><span class="mi">5</span><span class="n">pt</span><span class="p">,</span><span class="n">shorten</span> <span class="o">&lt;=</span><span class="mi">5</span><span class="n">pt</span><span class="p">,</span><span class="n">out</span><span class="o">=</span><span class="mi">70</span><span class="p">,</span><span class="ow">in</span><span class="o">=</span><span class="mi">130</span><span class="p">]</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.9</span><span class="n">cm</span><span class="p">,</span><span class="c">#1] (s.north) to (a.north);</span> <span class="o">%</span>\<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.45</span><span class="n">cm</span><span class="p">,</span><span class="c">#2] (a.north) to (b.north);</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.7</span><span class="n">cm</span><span class="p">,</span> <span class="c">#3] (b.north) to (f.north);</span> <span class="o">%</span>\<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">1.1</span><span class="n">cm</span><span class="p">,</span> <span class="c">#4] (c.north) to (d.north);</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.45</span><span class="n">cm</span><span class="p">,</span><span class="c">#5] (e.north) to (e.north);</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.45</span><span class="n">cm</span><span class="p">,</span><span class="c">#5] (f.north) to (f.north);</span> \<span class="n">end</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}</span> <span class="p">}</span> \<span class="n">newcommand</span><span class="p">{</span>\<span class="n">DrawBoxii</span><span class="p">}[</span><span class="mi">5</span><span class="p">]{</span> \<span class="n">begin</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}[</span><span class="n">overlay</span><span class="p">,</span><span class="n">remember</span> <span class="n">picture</span><span class="p">,</span><span class="o">-</span><span class="n">latex</span><span class="p">,</span><span class="n">shorten</span> <span class="o">&gt;=</span><span class="mi">5</span><span class="n">pt</span><span class="p">,</span><span class="n">shorten</span> <span class="o">&lt;=</span><span class="mi">5</span><span class="n">pt</span><span class="p">,</span><span class="n">out</span><span class="o">=</span><span class="mi">70</span><span class="p">,</span><span class="ow">in</span><span class="o">=</span><span class="mi">130</span><span class="p">]</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.45</span><span class="n">cm</span><span class="p">,</span><span class="c">#1] (s.north) to (a.north);</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.8</span><span class="n">cm</span><span class="p">,</span><span class="c">#2] (a.north) to (c.north);</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.9</span><span class="n">cm</span><span class="p">,</span> <span class="c">#3] (b.north) to (f.north);</span> \<span class="n">draw</span><span class="p">[</span><span class="n">distance</span><span class="o">=</span><span class="mf">0.45</span><span class="n">cm</span><span class="p">,</span><span class="c">#5] (e.north) to (e.north);</span> \<span class="n">end</span><span class="p">{</span><span class="n">tikzpicture</span><span class="p">}</span> <span class="p">}</span> \<span class="n">begin</span><span class="p">{</span><span class="n">document</span><span class="p">}</span> <span class="n">Schritt</span> <span class="mi">3</span> <span class="o">-</span> <span class="mf">1.0</span><span class="p">:</span> \<span class="n">begin</span><span class="p">{</span><span class="n">gather</span><span class="o">*</span><span class="p">}</span> <span class="o">%</span>\<span class="p">{</span><span class="n">D</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">d</span><span class="p">}</span>\<span class="p">}</span> <span class="o">~</span> \<span class="p">{</span><span class="n">S</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">s</span><span class="p">},</span> <span class="n">A</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">a</span><span class="p">},</span> <span class="n">B</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">b</span><span class="p">},</span> <span class="n">C</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">c</span><span class="p">},</span> <span class="n">E</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">e</span><span class="p">},</span> <span class="n">F</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">f</span><span class="p">}</span>\<span class="p">}</span> \<span class="n">DrawBoxi</span><span class="p">{</span><span class="n">red</span><span class="p">}{</span><span class="n">blue</span><span class="p">}{</span><span class="n">green</span><span class="p">}{</span><span class="n">purple</span><span class="p">}{</span><span class="n">orange</span><span class="p">}</span>\\ \<span class="n">end</span><span class="p">{</span><span class="n">gather</span><span class="o">*</span><span class="p">}</span> <span class="n">Schritt</span> <span class="mi">3</span> <span class="o">-</span> <span class="mf">1.1</span><span class="p">:</span> \<span class="n">begin</span><span class="p">{</span><span class="n">gather</span><span class="o">*</span><span class="p">}</span> <span class="o">%</span>\<span class="p">{</span><span class="n">C</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">c</span><span class="p">}</span>\<span class="p">}</span> <span class="o">~</span> \<span class="p">{</span><span class="n">D</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">d</span><span class="p">}</span>\<span class="p">}</span> <span class="o">~</span> \<span class="p">{</span><span class="n">S</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">s</span><span class="p">},</span> \<span class="n">tikzmark</span><span class="p">{</span><span class="n">a</span><span class="p">}</span><span class="n">A</span><span class="p">,</span> <span class="n">B</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">b</span><span class="p">},</span> <span class="n">E</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">e</span><span class="p">},</span> <span class="n">F</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">f</span><span class="p">}</span>\<span class="p">}</span> \<span class="n">DrawBoxii</span><span class="p">{</span><span class="n">red</span><span class="p">}{</span><span class="n">blue</span><span class="p">}{</span><span class="n">green</span><span class="p">}{</span><span class="n">purple</span><span class="p">}{</span><span class="n">orange</span><span class="p">}</span>\\ \<span class="n">end</span><span class="p">{</span><span class="n">gather</span><span class="o">*</span><span class="p">}</span> <span class="n">Schritt</span> <span class="mi">3</span> <span class="o">-</span> <span class="mf">2.0</span><span class="p">:</span> \<span class="n">begin</span><span class="p">{</span><span class="n">gather</span><span class="o">*</span><span class="p">}</span> \<span class="p">{</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">a</span><span class="p">}</span><span class="n">A</span>\<span class="p">}</span> <span class="o">~</span> \<span class="p">{</span><span class="n">C</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">c</span><span class="p">}</span>\<span class="p">}</span> <span class="o">~</span> \<span class="p">{</span><span class="n">D</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">d</span><span class="p">}</span>\<span class="p">}</span> <span class="o">~</span> \<span class="p">{</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">s</span><span class="p">}</span><span class="n">S</span><span class="p">,</span> \<span class="n">tikzmark</span><span class="p">{</span><span class="n">b</span><span class="p">}</span><span class="n">B</span><span class="p">,</span> <span class="n">E</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">e</span><span class="p">},</span> <span class="n">F</span>\<span class="n">tikzmark</span><span class="p">{</span><span class="n">f</span><span class="p">}</span>\<span class="p">}</span> \<span class="n">DrawBoxi</span><span class="p">{</span><span class="n">red</span><span class="p">}{</span><span class="n">blue</span><span class="p">}{</span><span class="n">green</span><span class="p">}{</span><span class="n">purple</span><span class="p">}{</span><span class="n">orange</span><span class="p">}</span>\\ \<span class="n">end</span><span class="p">{</span><span class="n">gather</span><span class="o">*</span><span class="p">}</span> \<span class="n">end</span><span class="p">{</span><span class="n">document</span><span class="p">}</span></code></pre></div> Linux Memory Consumption //martin-thoma.com/linux-memory-consumption/ Fri, 10 Feb 2012 21:04:45 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/linux-memory-consumption <h2>free</h2> <p>I’ve you want to check your memory consumption on a Linux machine, you can use free.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~<span class="sb">`</span><span class="nv">$ </span>free -m total used free shared buffers cached Mem: <span class="m">3952</span> <span class="m">2832</span> <span class="m">1119</span> <span class="m">0</span> <span class="m">117</span> 1565 -/+ buffers/cache: <span class="m">1150</span> 2802 Swap: <span class="m">8656</span> <span class="m">0</span> 8656</code></pre></div> <p>This means: I have a total of 3952 MB <a href="http://en.wikipedia.org/wiki/Random-access_memory">RAM</a>, used and free should be clear, shared is memory which is shared between processes, e.g. shared libraries. The “buffers” entry tells you how much of your RAM is being used for disk buffering. Over 8 GB got swapped out.</p> <h2>top</h2> <p>top will give you something like Windows’ task manager in the command line. If you press “M” it gets sorted by memory utilization:</p> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2012/02/top-memory.png"><img src="../images/2012/02/top-memory.png" alt="top sorted by memory utilization" width="" height="" class="size-full wp-image-13591" /></a><p class="wp-caption-text">top sorted by memory utilization</p></div> <h2>pmap</h2> <p>pmap reports a memory map of a process. Lets make an example. Eclipse has the process ID (pid) 4526 at the moment.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">pmap 4526</code></pre></div> <p>gives the following output:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">4526: /usr/lib/eclipse/eclipse Address Kbytes Mode Offset Device Mapping <span class="m">08048000</span> <span class="m">16</span> r-x-- <span class="m">0000000000000000</span> 008:00001 eclipse 0804c000 <span class="m">4</span> r---- <span class="m">0000000000003000</span> 008:00001 eclipse 0804d000 <span class="m">4</span> rw--- <span class="m">0000000000004000</span> 008:00001 eclipse 096c4000 <span class="m">11608</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 62e40000 <span class="m">43776</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> <span class="m">65900000</span> <span class="m">130944</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 6d8e0000 <span class="m">87424</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 72e40000 <span class="m">262144</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 82e40000 <span class="m">44800</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 85a00000 <span class="m">512</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 85a80000 <span class="m">216832</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> 92e40000 <span class="m">6312</span> r--s- <span class="m">0000000000001000</span> 008:00001 classes.jsa 9346a000 <span class="m">3928</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> <span class="m">93840000</span> <span class="m">7412</span> rw--- 000000000062b000 008:00001 classes.jsa 93f7d000 <span class="m">4876</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> <span class="m">94440000</span> <span class="m">904</span> rw--- 0000000000d68000 008:00001 classes.jsa <span class="m">94522000</span> <span class="m">3192</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> <span class="m">94840000</span> <span class="m">32</span> r-xs- 0000000000e4a000 008:00001 classes.jsa <span class="m">94848000</span> <span class="m">4064</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b17f5000 <span class="m">44</span> r--s- <span class="m">0000000000070000</span> 008:00001 org.eclipse.jdt.junit_3.5.2.r352_v20100113-0800.jar b1800000 <span class="m">144</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b1824000 <span class="m">880</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b1909000 <span class="m">12</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b190c000 <span class="m">312</span> rwx-- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b195a000 <span class="m">12</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b195d000 <span class="m">312</span> rwx-- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b19ab000 <span class="m">12</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b19ae000 <span class="m">312</span> rwx-- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b19fc000 <span class="m">12</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b19ff000 <span class="m">312</span> rwx-- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b1a4d000 <span class="m">16</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libattr.so.1.1.0 b1a51000 <span class="m">4</span> r---- <span class="m">0000000000003000</span> 008:00001 libattr.so.1.1.0 b1a52000 <span class="m">4</span> rw--- <span class="m">0000000000004000</span> 008:00001 libattr.so.1.1.0 b1a53000 <span class="m">24</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libfam.so.0.0.0 b1a59000 <span class="m">4</span> r---- <span class="m">0000000000006000</span> 008:00001 libfam.so.0.0.0 b1a5a000 <span class="m">4</span> rw--- <span class="m">0000000000007000</span> 008:00001 libfam.so.0.0.0 b1a5b000 <span class="m">24</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libacl.so.1.1.0 b1a61000 <span class="m">4</span> r---- <span class="m">0000000000006000</span> 008:00001 libacl.so.1.1.0 b1a62000 <span class="m">4</span> rw--- <span class="m">0000000000007000</span> 008:00001 libacl.so.1.1.0 b1a63000 <span class="m">48</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libfile.so b1a6f000 <span class="m">4</span> r---- 000000000000b000 008:00001 libfile.so b1a70000 <span class="m">4</span> rw--- 000000000000c000 008:00001 libfile.so b1a71000 <span class="m">100</span> r--s- <span class="m">0000000000000000</span> 008:00001 mime.cache b1a8a000 <span class="m">12</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libgpg-error.so.0.4.0 b1a8d000 <span class="m">4</span> r---- <span class="m">0000000000002000</span> 008:00001 libgpg-error.so.0.4.0 <span class="o">[</span>...<span class="o">]</span> b755a000 <span class="m">4</span> r--s- <span class="m">0000000000001000</span> 008:00001 runtime_registry_compatibility.jar b755b000 <span class="m">4</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b755c000 <span class="m">28</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libvorbisfile.so.3.3.2 b7563000 <span class="m">4</span> r---- <span class="m">0000000000006000</span> 008:00001 libvorbisfile.so.3.3.2 b7564000 <span class="m">4</span> rw--- <span class="m">0000000000007000</span> 008:00001 libvorbisfile.so.3.3.2 b7565000 <span class="m">16</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libcanberra-gtk-module.so b7569000 <span class="m">4</span> ----- <span class="m">0000000000004000</span> 008:00001 libcanberra-gtk-module.so b756a000 <span class="m">4</span> r---- <span class="m">0000000000004000</span> 008:00001 libcanberra-gtk-module.so b756b000 <span class="m">4</span> rw--- <span class="m">0000000000005000</span> 008:00001 libcanberra-gtk-module.so b756c000 <span class="m">44</span> r-x-- <span class="m">0000000000000000</span> 008:00001 eclipse_1208.so b7577000 <span class="m">4</span> r---- 000000000000a000 008:00001 eclipse_1208.so b7578000 <span class="m">4</span> rw--- 000000000000b000 008:00001 eclipse_1208.so b7579000 <span class="m">252</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_CTYPE b75b8000 <span class="m">1144</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_COLLATE b76d6000 <span class="m">4</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b76d7000 <span class="m">1356</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libc-2.11.1.so b782a000 <span class="m">4</span> ----- <span class="m">0000000000153000</span> 008:00001 libc-2.11.1.so b782b000 <span class="m">8</span> r---- <span class="m">0000000000153000</span> 008:00001 libc-2.11.1.so b782d000 <span class="m">4</span> rw--- <span class="m">0000000000155000</span> 008:00001 libc-2.11.1.so b782e000 <span class="m">16</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b7832000 <span class="m">8</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libdl-2.11.1.so b7834000 <span class="m">4</span> r---- <span class="m">0000000000001000</span> 008:00001 libdl-2.11.1.so b7835000 <span class="m">4</span> rw--- <span class="m">0000000000002000</span> 008:00001 libdl-2.11.1.so b7836000 <span class="m">84</span> r-x-- <span class="m">0000000000000000</span> 008:00001 libpthread-2.11.1.so b784b000 <span class="m">4</span> r---- <span class="m">0000000000014000</span> 008:00001 libpthread-2.11.1.so b784c000 <span class="m">4</span> rw--- <span class="m">0000000000015000</span> 008:00001 libpthread-2.11.1.so b784d000 <span class="m">8</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b784f000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b7850000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_NUMERIC b7851000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_TIME b7852000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_MONETARY b7853000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 SYS_LC_MESSAGES b7854000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_PAPER b7855000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_NAME b7856000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_ADDRESS b7857000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_TELEPHONE b7858000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_MEASUREMENT b7859000 <span class="m">28</span> r--s- <span class="m">0000000000000000</span> 008:00001 gconv-modules.cache b7860000 <span class="m">4</span> r---- <span class="m">0000000000000000</span> 008:00001 LC_IDENTIFICATION b7861000 <span class="m">8</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b7863000 <span class="m">4</span> r-x-- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> b7864000 <span class="m">108</span> r-x-- <span class="m">0000000000000000</span> 008:00001 ld-2.11.1.so b787f000 <span class="m">4</span> r---- 000000000001a000 008:00001 ld-2.11.1.so b7880000 <span class="m">4</span> rw--- 000000000001b000 008:00001 ld-2.11.1.so bfa49000 <span class="m">12</span> ----- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> bfa4d000 <span class="m">304</span> rwx-- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> stack <span class="o">]</span> bfa99000 <span class="m">4</span> rw--- <span class="m">0000000000000000</span> 000:00000 <span class="o">[</span> anon <span class="o">]</span> mapped: 927836K writeable/private: 881752K shared: 13572K</code></pre></div> <p>So at the moment eclipse is using 927MB of virtual memory. But it need “only” about 186 MB real, physical memory. According to <a href="http://virtualthreads.blogspot.com/2006/02/understanding-memory-usage-on-linux.html">virtualthreads.blogspot.com</a> all data segments have the access rights rw— and all code segments have the rights r-x–.</p> <h2>vmstat</h2> <p>Virtual memory statistics gives you the following information:</p> <p>Here is the example:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~<span class="nv">$`</span> vmstat procs -----------memory---------- ---swap-- -----io---- -system-- ----cpu---- r b swpd free buff cache si so bi bo in cs us sy id wa <span class="m">0</span> <span class="m">0</span> <span class="m">0</span> <span class="m">1120696</span> <span class="m">119948</span> <span class="m">1599112</span> <span class="m">0</span> <span class="m">0</span> <span class="m">21</span> <span class="m">35</span> <span class="m">416</span> <span class="m">116</span> <span class="m">12</span> <span class="m">5</span> <span class="m">82</span> 1</code></pre></div> <p>–memory– <strong>swpd</strong>: sum of the used virtual memory. <strong>free</strong>: amount of unused physical memory. <strong>buff</strong>: amount of physical memory which gets used as disc-buffer. <strong>cache</strong>: amount of physical memory which gets used as cache. –swap– <strong>si</strong>: amount of memory which gets loaded from hdd to your RAM. If this is positive, you need more RAM. <strong>so</strong>: amount of memory which gets loaded from RAM to hdd. –io– <strong>bi</strong>: input of block devices <strong>bo</strong>: output of block devices –system– <strong>in</strong>: Number of interrupts per second <strong>cs</strong>: Context-switches per second –cpu– <strong>us</strong>: CPU time spent for user processes <strong>sy</strong>: CPU time spent for kernel processes <strong>id</strong>: idle processor time <strong>wa</strong>: Waiting for input / output</p> <h2>Sources</h2> <ul> <li><a href="http://linuxwiki.de/vmstat">LinuxWiki</a> (German)</li> <li><a href="http://www.cyberciti.biz/faq/linux-check-memory-usage/">cyberciti.biz</a></li> </ul> Wahrscheinlichkeitstheorie - Klausur //martin-thoma.com/wt-klausur/ Tue, 07 Feb 2012 16:29:52 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wt-klausur <p>Morgen schreibe ich eine Klausur in Wahrscheinlichkeitstheorie. Zum Glück dürfen wir das Skript und Notizen mitnehmen.</p> <p>Diesen netten, kleinen <a href="../images/2012/02/wt-cheat-sheet.pdf">Zettel mit Formeln</a> habe ich gerade erstellt. Falls ihr die LaTeX-Datei anpassen wollt, könnt ihr sie <a href="../images/2012/02/wt-cheat-sheet.zip">hier</a> herunterladen.</p> <p><a href="http://www.math.kit.edu/stoch/lehre/wtinf2011w">Hier</a> noch ein paar Hinweise:</p> <p>Klausur Informatik: 08. Februar 2012, <strong>17.45 – 19.15 Uhr</strong>.</p> <ul> <li>Teilnehmer mit Nachnamen <strong>Aa -- Kon</strong> schreiben die Klausur im Audimax, Geb. 30.95 </li> <li>Teilnehmer mit Nachnamen <strong>Kor -- Zz</strong> schreiben die Klausur im Gerthsen-Hörsaal, Geb.&nbsp;30.21 </li> </ul> <h2 id="material">Material</h2> <ul> <li>Skript im Skripteverkauf</li> <li><a href="http://colah.github.io/posts/2015-09-Visual-Information/">Visual Information Theory</a></li> </ul> <h2 id="nicht-vergessen">Nicht vergessen</h2> <ul> <li>Skript + Mitschrift</li> <li>Studentenausweis</li> <li>Taschenrechner</li> <li>Kugelschreiber</li> </ul> Stop ACTA //martin-thoma.com/stop-acta/ Sat, 28 Jan 2012 21:19:39 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/stop-acta <div style="width: 138px" class="wp-caption alignright"><a href="../images/2012/01/acta-krake.png"><img src="../images/2012/01/acta-krake.png" alt="ACTA Krake" width="" height="" class="size-full wp-image-13091" /></a><p class="wp-caption-text">Stopp ACTA!</p></div> <h2>What is ACTA?</h2> <p>The Anti-Counterfeiting Trade Agreement (ACTA) is a trade agreement between the following states:</p> <ul> <li>United States: signed 1 October 2011 in Tokyo</li> <li>Australia: signed 1 October 2011 in Tokyo</li> <li>Canada: signed 1 October 2011 in Tokyo</li> <li>Japan: signed 1 October 2011 in Tokyo</li> <li>Morocco: signed 1 October 2011 in Tokyo</li> <li>New Zealand: signed 1 October 2011 in Tokyo</li> <li>Singapore: signed 1 October 2011 in Tokyo</li> <li>South Korea: signed 1 October 2011 in Tokyo</li> <li>European Union and 22 Member States: signed on 26 January 2012; final enactment into law is on hold pending a debate in the European Parliament in June 2012. <ul> <li>Germany: not signed yet</li> <li>Cyprus: not signed yet</li> <li>Estonia: not signed yet</li> <li>Netherlands: not signed yet</li> <li>Slovakia: not signed yet</li> </ul> </li> <li>Mexico: </li> <li>Switzerland: </li> </ul> <p>Those countries describe it as a response “to the increase in global trade of counterfeit goods and pirated copyright protected works.” It would create a governing body outside international institutions such as the World Trade Organization (WTO), the World Intellectual Property Organization (WIPO) or the United Nations. The scope of ACTA includes counterfeit goods, generic medicines and copyright infringement on the Internet.</p> <p>An official Summary of Key Elements Under Discussion published November 2009 states that “ACTA aims to build on existing international rules in the area of intellectual property, in particular on the TRIPS Agreement, and is intended to address a number of enforcement issues where participants have identified that an international legal framework does not exist or needs to be strengthened.”</p> <p>On 10 March 2010, the European Parliament adopted a resolution criticizing the ACTA with 663 in favor of the resolution and 13 against, arguing that “in order to respect fundamental rights, such as the right to freedom of expression and the right to privacy” certain changes in the ACTA content and the process should be made.</p> <h2>Who is for ACTA?</h2> <p>Well, I guess the signing government and parliaments. I’ve also heard that <a href="http://en.wikipedia.org/wiki/MPAA">MPAA</a> is for ACTA (<a href="http://www.mpaa.org/resources/eea2c91a-7608-4b3a-9305-ec414c47b67f.pdf">source</a>).</p> <h2>Who is against ACTA?</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Electronic_Frontier_Foundation">Electronic Frontier Foundation</a> (EFF)</li> <li><a href="http://en.wikipedia.org/wiki/Chaos_Computer_Club">Chaos Computer Club</a></li> <li>several pirate partys, e.g. the German Piratenpartei (<a href="http://web.piratenpartei.de/papiere/2010/acta">source</a>)</li> </ul> <h3>And why?</h3> <iframe width="560" height="315" src="http://www.youtube.com/embed/citzRjwk-sQ" frameborder="0" allowfullscreen=""></iframe> <ul> <li>treaty will restrict fundamental civil and digital rights: <ul> <li>freedom of expression</li> <li>communication privacy</li> </ul> </li> <li>removal of "legal safeguards that protect Internet Service Providers from liability for the actions of their subscribers" in effect giving ISPs no option but to comply with privacy invasions</li> </ul> <h2>See also</h2> <ul> <li>Wikpedia: <a href="http://en.wikipedia.org/wiki/Anti-Counterfeiting_Trade_Agreement">ACTA</a> (big parts of my article are from this wiki-article)</li> <li><a href="http://freeknowledge.eu/acta-a-global-threat-to-freedoms-open-letter">open letter 1</a></li> <li><a href="http://www.avaaz.org/de/eu_save_the_internet_spread/?wabjtbb">Save the Internet</a></li> <li><a href="http://www.stopp-acta.info/">STOPP ACTA</a></li> <li><a href="http://www.thejournal.ie/french-mep-quits-and-slams-acta-process-as-a-charade-338453-Jan2012/">French MEP quits and slams ACTA process as &lsquo;a charade&rsquo;</a></li> </ul> Sprachen, Automaten und Grammatiken: Ein Überblick //martin-thoma.com/sprachen-automaten-und-grammatiken/ Sat, 28 Jan 2012 10:52:34 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sprachen-automaten-und-grammatiken <p>Die folgende Tabelle gibt einen Überblick über formale Sprachen, die Automaten die sie akzeptieren und die Grammatiken, die sie erzeugen. Dabei haben die Grammatiken die Form <code>$G = (V, \Sigma, P, S)$</code>:</p> <ul> <li>V: Die Menge der Nicht-Terminale. Für sie benutze ich Gro&szlig;buchstaben.</li> <li>`$\Sigma$`: Die Menge der Terminale. Für sie benutze ich Kleinbuchstaben.</li> <li>P: Die Produktion, also die Regeln mit denen die Grammatik die Sprache erzeugt. Nur diese hat unterschiedliche Bedingungen, je nach dem welchem Typ die Grammatik angeh&ouml;rt.</li> <li>S: Das Startsymbol aus `$\Sigma$`.</li> </ul> <table> <tr> <th rowspan="2">Typ <th rowspan="2">Bezeichnung <th rowspan="2">Regeln <th colspan="4">Abgeschlossen unter <th rowspan="2">Modell <tr> <th>`$\cup$`</th> <th>`$\cap$`</th> <th>`$\cdot$`</th> <th>`${}^C$`</th> </tr> <tr> <td style="background-color:#F08080;">0</td> <td>semientscheidbar</td> <td>alles</td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></td> <td>D. <a href="http://de.wikipedia.org/wiki/Turingmaschine">Turingmaschine</a>, ND. Turingmaschine</td> </tr> <tr> <td style="background-color:#90EE90;">1</td> <td><a href="http://de.wikipedia.org/wiki/Kontextsensitive_Grammatik">kontextsensitiv</a></td> <td>`$u \rightarrow v, |a| \leq |v|$`</td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td>(ND.?) L&auml;ngenbeschr&auml;nkter Automat</td> </tr> <tr> <td style="background-color:#90EE90;">2</td> <td><a href="http://de.wikipedia.org/wiki/Kontextfreie_Grammatik">kontextfrei</a></td> <td>`$A \rightarrow v$`</td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/no.png" alt="no" title="no" width="13" height="13" class="alignnone size-full wp-image-12961" /></td> <td>ND. <a href="http://de.wikipedia.org/wiki/Kellerautomat">Kellerautomat</a></td> </tr> <tr> <td style="background-color:#90EE90;">3</td> <td><a href="http://de.wikipedia.org/wiki/Regul%C3%A4re_Grammatik">regul&auml;r</a></td> <td>`$A \rightarrow \varepsilon, A \rightarrow aB$`</td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><img src="../images/2012/01/yes.png" alt="yes" title="yes" width="13" height="13" class="size-full wp-image-12931" /></td> <td><a href="http://de.wikipedia.org/wiki/Endlicher_Automat">Endliche Automaten</a> (<a href="http://de.wikipedia.org/wiki/Moore-Automat">Moore</a>, <a href="http://de.wikipedia.org/wiki/Mealy-Automat">Mealy</a>, <a href="http://de.wikipedia.org/wiki/Akzeptor_(Informatik)">Akzeptoren</a>)</td> </tr> <strong>Legende:</strong> Typ.: Der Typ der Grammatik in der <a href="http://de.wikipedia.org/wiki/Chomsky-Hierarchie">Chomsky-Hierarchie</a> D.: "Deterministisch" ND.: "Nicht Deterministisch" <span style="background-color:#F08080;">semi-entscheidbar</span> <span style="background-color:#90EE90;">entscheidbar</span>, es kann also in endlicher Zeit entschieden werden, ob ein Wort in der Sprache liegt (vgl. <a href="http://de.wikipedia.org/wiki/Wortproblem">Wortproblem</a>). <strong>Nicht-Abeschlossenheit der Kontextfreien Sprachen:</strong> `$L_1 = \{a^jb^ic^i | j \in \mathbb{N}_0, i \in \mathbb{N}_0\}$` `$L_2 = \{a^ib^ic^j | j \in \mathbb{N}_0, i \in \mathbb{N}_0\}$` `$L_1 \cap L_2 = \{a^ib^ic^i | i \in \mathbb{N}_0\}$` `$(L_1 \cup L_2)^C = L_1^C \cap L_2^C$` <h2>Weitere Aussagen</h2> Sei L eine Sprache. `$L \in {\cal L_3} \Leftrightarrow$` Es existiert ein regul&auml;rer Ausdruck für L. `$L \in {\cal L_3} \Leftrightarrow$` Die Anzahl der &Auml;quivalenzklassen der <a href="http://de.wikipedia.org/wiki/Nerode-Relation">Nerode-Relation</a> bzgl. der Sprache ist endlich. `$L \in {\cal L_3} \Rightarrow$` Das <a href="../pumping-lemma/" title="Beweis durch Widerspruch: Eine Sprache ist nicht regul&auml;r (Pumping-Lemma)">Pumping-Lemma</a> ist erfüllt. Für regul&auml;re Sprachen ist das Leerheitsproblem (`$L(G) \stackrel{?}{=} \emptyset$`) entscheidbar. Für regul&auml;re Sprachen ist das Endlichkeitsproblem (`$L(G) \stackrel{?}{&lt;} \infty$`) entscheidbar. Für kontextfreie Sprachen ist das Leerheitsproblem entscheidbar. Für kontextfreie Sprachen ist das Endlichkeitsproblem entscheidbar. Für Typ 0 und Typ 1 Sprachen ist das Leerheitsproblem nicht entscheidbar. `$L \in {\cal L_2} \Leftrightarrow L$` wird von einem nichtdeterministischem Kellerautomaten erkannt. <h2>Quellen</h2> <ul> <li>Uwe Sch&ouml;ning: <i>Theoretische Informatik- kurz gefasst</i>. 5.&nbsp;Auflage. Spektrum Akademischer Verlag, Heidelberg <span style="white-space:nowrap;">2008</span>, ISBN 978-3-8274-1824-1, <span class="plainlinks-print"><a rel="nofollow" class="external text" href="http://d-nb.info/986529222">DNB 986529222</a></span>.</li> <li>Tutorium, Skript, Vorlesung: Theoretische Grundlagen der Informatik am KIT bei Prof. Dr. Dorothea Wagner</li> </ul> </th></th></th></th></th></tr></table> Plotting function graphs with LaTeX //martin-thoma.com/plotting-function-graphs-with-latex/ Sat, 28 Jan 2012 00:17:26 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/plotting-function-graphs-with-latex <p>It’s crazy how much time I have wasted today just for searching for a working example how to plot a function within LaTeX. Here are two complete examples which worked for me.</p> <p>I have used this command to generate the PDF-file:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pdflatex latex.tex -output-format=pdf </pre></div> </div> </div> <h2>gnuplot</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/01/gnuplot-300x246.png"><img src="../images/2012/01/gnuplot-300x246.png" alt="gnuplot" width="" height="" class="size-medium wp-image-12781" /></a><p class="wp-caption-text">gnuplot</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{article} \usepackage{tikz} \usepackage{pgfplots} \begin{document} \begin{tikzpicture} \begin{axis} \addplot+[id=parable,domain=-5:5] gnuplot{4*x**2 - 5} node[pin=180:{$4x^2-5$}]{}; \end{axis} \end{tikzpicture} \end{document} </pre></div> </div> </div> <h2>tikzpicture</h2> <div style="width: 190px" class="wp-caption aligncenter"><a href="../images/2012/01/tikzpicture1-180x300.png"><img src="../images/2012/01/tikzpicture1-180x300.png" alt="tikzpicture" width="" height="" class="size-medium wp-image-12821" /></a><p class="wp-caption-text">tikzpicture</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{article} \usepackage{tikz} \begin{document} \begin{tikzpicture} \draw[very thin,color=gray] (0.0,0.0) grid (1.8,3.8); \draw[-&gt;] (-0.5,0) -- (2,0) node[right] {$x$}; \draw[-&gt;] (0,-0.5) -- (0,4) node[above] {$y$}; \draw [domain=0:1/3,red] plot (\x,3*3*\x); \draw [domain=1/3:2/3,red] plot (\x,2*3-3*3*\x); \draw [domain=2/3:1.5,red] plot (\x,0); \draw [domain=0:1/4,orange] plot (\x,4*4*\x); \draw [domain=1/4:2/4,orange] plot (\x,2*4-4*4*\x); \draw [domain=2/4:1.5,orange] plot (\x,0); \end{tikzpicture} \end{document} </pre></div> </div> </div> <h2>Floating text</h2> <p>If you want to wrap the text around the graph, you can use wrapfigure:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{article} \usepackage{tikz} \usepackage{pgfplots} \usepackage{wrapfig} \begin{document} \begin{wrapfigure}{r}{.2\textwidth} \begin{center} \begin{tikzpicture} \draw[-&gt;] (-0.5,0) -- (2,0) node[right] {$x$}; \draw[-&gt;] (0,-0.5) -- (0,4) node[above] {$y$}; \draw [domain=0:1/3,red] plot (\x,3*3*\x); \draw [domain=1/3:2/3,red] plot (\x,2*3-3*3*\x); \draw [domain=2/3:1.5,red] plot (\x,0); \draw [domain=0:1/4,orange] plot (\x,4*4*\x); \draw [domain=1/4:2/4,orange] plot (\x,2*4-4*4*\x); \draw [domain=2/4:1.5,orange] plot (\x,0); \end{tikzpicture} \end{center} \end{wrapfigure} Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis congue dictum elit. Morbi ultricies laoreet massa, sed sagittis lorem laoreet et. Donec at erat non sem tristique rutrum vel vel justo. Vestibulum tincidunt pulvinar mi, a congue purus dignissim vel. Ut porttitor dignissim neque eget rutrum. Nunc gravida varius semper. Quisque et purus quam. Quisque ultricies tristique magna sit amet egestas. Mauris bibendum lacus semper justo consectetur blandit vitae non nisi. Etiam non augue nec est facilisis tempor. Nullam non diam vel erat fermentum gravida. Proin tincidunt turpis lobortis ante elementum suscipit. Curabitur congue, dolor fringilla feugiat blandit, quam libero euismod purus, eget commodo erat nibh a augue. Vestibulum ut tellus ac arcu semper facilisis. \end{document} </pre></div> </div> </div> <h2>PSTricks</h2> <p>I have found <a href="http://www.tn-home.de/Tobias/Soft/TeX/TUG040611/presentation.pdf">some</a> <a href="http://en.wikipedia.org/wiki/PSTricks">very</a> <a href="http://www.siart.de/typografie/pstricks_20030809.pdf">nice</a> <a href="http://mirror.informatik.uni-mannheim.de/pub/mirrors/tex-archive/graphics/pstricks/contrib/pst-3dplot/pst-3dplot-doc.pdf">example</a> <a href="http://www.ursoswald.ch/LaTeXGraphics/pstricks/pstricks.html">images</a>, but no working LaTeX-Code.</p> <h2>Read more</h2> <ul> <li>Wikibooks: <a href="http://en.wikibooks.org/wiki/LaTeX/Floats,_Figures_and_Captions">LaTeX/Floats, Figures and Captions</a></li> <li><a href="http://ftp.math.purdue.edu/mirrors/ctan.org/graphics/pgf/contrib/pgfplots/doc/latex/pgfplots/pgfplots.pdf">Manual for pgfplots</a> with lots of examples (as images and LaTeX in over 300 pages!)</li> <li>TeXample.net: <a href="http://www.texample.net/tikz/examples/gnuplot-basics/">GNUPLOT basics</a>, <a href="http://www.texample.net/tikz/examples/parameterized-plots/">Parameterized plots</a>, <a href="http://www.texample.net/tikz/examples/pgfplots/">Pgfplots</a></li> </ul> Check Computer / Hardware for Linux-compatibility //martin-thoma.com/check-computer-hardware-for-linux-compatibility/ Fri, 27 Jan 2012 20:42:21 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/check-computer-hardware-for-linux-compatibility <p>Linux users who are not very skilled have a big problem: If they want to buy a new computer or new hardware, it is very difficult for them to find out if something works or not. I’ll give you some hints how you could find it out:</p> <h2>Debian device driver check &amp; report</h2> <p><a href="http://kmuto.jp/debian/hcl/">This site</a> checks your whole system. You only need to boot a Linux system (e.g. via <a href="http://en.wikipedia.org/wiki/Live_CD">LiveCD</a>) and execute:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci -n</code></pre></div> <p>in the terminal (which pops up if you type Ctrl + Alt + T). Copy it, paste it into the provided form and you will get a list of your hardware and simply “Yes” if this component works with Debian.</p> <h2>Linux HCL</h2> <p>The <a href="http://linuxhcl.com/">Linux HCL</a> provides a lot of hand-written reviews of users. Here is my <a href="http://linuxhcl.com/browse/product?id=7719">review of my notebook</a>.</p> <h2>UbuntuUsers</h2> <p>German users might want to take a look at the wiki-article “<a href="http://wiki.ubuntuusers.de/Hardwaredatenbanken">Hardwaredatenbanken</a>”.</p> Impact of SOPA protests //martin-thoma.com/impact-of-sopa-protests/ Tue, 24 Jan 2012 08:06:41 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/impact-of-sopa-protests <p>It seems as if the SOPA protests were quite effective. 162 Millionen visitors of Wikipedia did see the message. <a href="http://www.facebook.com/zuck/posts/10100210345757211">Zuckerbergs Facebook post</a> got half a million Likes. Thousands bloggers downloaded protest plugins which blacked out their blog.</p> <div style="width: 250px" class="wp-caption aligncenter"><a href="../images/2012/01/sopa-protests-congress-supporters-opponents-240x300.jpg"><img src="../images/2012/01/sopa-protests-congress-supporters-opponents-240x300.jpg" alt="Members of Congress position on SOPA/PIPA (found on boingboing.net)" width="" height="" class="size-medium wp-image-12661" /></a><p class="wp-caption-text">Members of Congress position on SOPA/PIPA (found on &lt;a href=http://boingboing.net/wp-content/uploads/2012/01/201201191642.jpg&gt;boingboing.net)</p></div> <h2>See also</h2> <ul> <li><a href="http://projects.propublica.org/sopa/">SOPA Opera</a>: Where Do Your Members of Congress Stand on SOPA and PIPA?</li> <li><a href="http://arstechnica.com/tech-policy/news/2012/01/pipa-support-collapses-with-13-new-opponents-in-senate.ars">ArsTechnica</a>: PIPA support collapses, with 13 new Senators opposed</li> <li><a href="http://en.wikipedia.org/wiki/Protests_against_SOPA_and_PIPA">Wikipedia</a>: Protests against SOPA and PIPA</li> <li>German News: <a href="http://www.heise.de/newsticker/meldung/Proteste-gegen-PIPA-und-SOPA-zeigen-Erfolge-1416809.html">heise</a>, <a href="http://www.heise.de/newsticker/meldung/US-Senat-verschiebt-Abstimmung-ueber-Zensurgesetz-1418544.html">heise</a>, <a href="http://www.golem.de/1201/89174.html">Golem</a>, <a href="http://www.golem.de/1201/89229.html">Golem</a></li> </ul> SOPA protests //martin-thoma.com/sopa-protests/ Wed, 18 Jan 2012 08:29:42 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/sopa-protests <p>Some of the biggest sites in the internet are currently calling US citizens up to protest. SOPA - the Stop Online Piracy Act - is endangering some key aspects of the internet.</p> <p>I am a little bit disappointed that Google had no special doodle today and twitter had no message at all ☹ Well, at least did Google offer <a href="https://www.google.com/landing/takeaction/">some information</a>.</p> <p>Here is a neat explanation of SOPA:</p> <iframe src="http://player.vimeo.com/video/31100268?byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <h2>Wikipedia</h2> <p>Completely blacked out: <a href="../images/2012/01/sopa-wikipedia.png"><img src="../images/2012/01/sopa-wikipedia-300x141.png" alt="" title="Wikipedia SOPA protests" width="300" height="141" class="aligncenter size-medium wp-image-12401" /></a> Twitter: #WikipediaBlackout</p> <p>By the way, if you disable JavaScript you can view Wikipedia as always.</p> <h2>German Wiki</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/01/sopa-wiki-de-300x81.png"><img src="../images/2012/01/sopa-wiki-de-300x81.png" alt="German Wikipedia SOPA protests" width="" height="" class="size-medium wp-image-12411" /></a><p class="wp-caption-text">German Wikipedia SOPA protests</p></div> <h2>The Oatmeal</h2> <p><a href="http://theoatmeal.com/sopa">The Oatmeal</a> has also completely blacked out its website:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/01/sopa-oatmeal-300x241.png"><img src="../images/2012/01/sopa-oatmeal-300x241.png" alt="Oatmeals SOPA protest" width="" height="" class="size-medium wp-image-12541" /></a><p class="wp-caption-text">Oatmeals SOPA protest</p></div> <h2>Zachstronaut</h2> <p><a href="http://www.zachstronaut.com/lab/text-shadow-box/stop-sopa.html">zachstronaut.com</a> offers an interactive one:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/01/sopa-zachstronaut-300x154.png"><img src="../images/2012/01/sopa-zachstronaut-300x154.png" alt="SOPA - Zachstronaut protests" width="" height="" class="size-medium wp-image-12461" /></a><p class="wp-caption-text">SOPA - Zachstronaut protests</p></div> <h2>Boing Boing</h2> <p><a href="http://boingboing.net/2012/01/14/boing-boing-will-go-dark-on-ja.html">Boing Boing</a> is completely blacked out:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/01/sopa-boingboing-300x140.png"><img src="../images/2012/01/sopa-boingboing-300x140.png" alt="SOPA - BoingBoing protest" width="" height="" class="size-medium wp-image-12451" /></a><p class="wp-caption-text">SOPA - BoingBoing protest</p></div> <h2>Tucows</h2> <p>Tucows - a site with $80.939 million USD revenue - offers some information and a <a href="http://tucowsinc.com/news/2012/01/why-we-dont-like-sopa/">link</a> on the top. They normally offer shareware and freeware:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2012/01/sopa-tucowsinc-300x182.png"><img src="../images/2012/01/sopa-tucowsinc-300x182.png" alt="SOPA Tucowsinc" width="" height="" class="size-medium wp-image-12431" /></a><p class="wp-caption-text">SOPA Tucowsinc</p></div> <h2>Notes</h2> <p>Many big companies (AOL, eBay, Facebook, Google, LinkedIn, mozilla, twitter, Yahoo, zynga) wrote <a href="http://www.protectinnovation.com/downloads/letter.pdf">a letter</a> to the Committee on the Judiciary.</p> <h2>Participate</h2> <p>If you want to participate, take a look at <a href="http://sopastrike.com/">SOPAstrike.com</a>, <a href="http://AmericanCensorship.org/">americancensorship.org</a> or <a href="https://twitter.com/#!/search/realtime/%23StrikeTools">#striketools</a>.</p> <h2>Additional</h2> <object width="526" height="374"> <param name="movie" value="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" /> <param name="allowFullScreen" value="true" /> <param name="allowScriptAccess" value="always" /> <param name="wmode" value="transparent" /> <param name="bgColor" value="#ffffff" /> <param name="flashvars" value="vu=http://video.ted.com/talk/stream/2012S/Blank/ClayShirky_2012S-320k.mp4&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/ClayShirky_2012S-embed.jpg&amp;vw=512&amp;vh=288&amp;ap=0&amp;ti=1329&amp;lang=en&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=defend_our_freedom_to_share_or_why_sopa_is_a_bad_idea;year=2012;theme=media_that_matters;theme=master_storytellers;event=TEDSalon+NY2012;tag=Business;tag=Technology;tag=creativity;tag=media;tag=politics;&amp;preAdTag=tconf.ted/embed;tile=1;sz=512x288;" /> <embed src="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" pluginspace="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" wmode="transparent" bgcolor="#ffffff" width="526" height="374" allowfullscreen="true" allowscriptaccess="always" flashvars="vu=http://video.ted.com/talk/stream/2012S/Blank/ClayShirky_2012S-320k.mp4&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/ClayShirky_2012S-embed.jpg&amp;vw=512&amp;vh=288&amp;ap=0&amp;ti=1329&amp;lang=en&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=defend_our_freedom_to_share_or_why_sopa_is_a_bad_idea;year=2012;theme=media_that_matters;theme=master_storytellers;event=TEDSalon+NY2012;tag=Business;tag=Technology;tag=creativity;tag=media;tag=politics;&amp;preAdTag=tconf.ted/embed;tile=1;sz=512x288;" /> </object> <ul> <li>Paper of the <a href="https://www.eff.org/sites/default/files/One-Page-SOPA_0.pdf">Electronic Frontier Foundation</a> and <a href="https://www.eff.org/free-speech-weak-link">web page</a></li> <li>Position of <a href="http://dyn.com/sopa-breaking-dns-parasite-stop-online-piracy/">dyn.com</a></li> <li>Position of <a href="http://xkcd.com/1005/">xkcd</a></li> </ul> Bachelor Informatik, 1. Semester: Was bisher geschah //martin-thoma.com/bachelor-informatik-1-semester-was-bisher-geschah/ Sun, 08 Jan 2012 20:38:41 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/bachelor-informatik-1-semester-was-bisher-geschah <p>Die erste Hälfte des Semesters ist nun vorbei und es wird Zeit zu wiederholen, was man wissen sollte. Eventuell ist diese Liste für ein paar Kommilitonen von nutzen. Wenn man gerade eines der Module macht, sollte man alles wissen, was in den Links steht. Naja, vielleicht nicht alles, aber man sollte auf jeden Fall die Begriffe im Schlaf definieren können. Die Links sind meist deutsche Wiki-Artikel, manchmal auch englische. Je nach dem, was ich besser fand.</p> <p>Einiges hätte ich bei vielen Modulen schreiben können, z.B. der Beweis durch Induktion. Ich habe mir dann einfach eines ausgesucht und es nur da hinein geschrieben. Das ist eh schon lang genug.</p> <h2>1. Semester</h2> <h3>Analysis I</h3> <h4>Fachbegriffe</h4> <ul> <li><strong>Verkn&uuml;pfungseigenschaften</strong>: <a href="http://de.wikipedia.org/wiki/Kommutativgesetz">Kommutativgesetz</a>, <a href="http://de.wikipedia.org/wiki/Assoziativgesetz">Assoziativgesetz</a>, <a href="http://de.wikipedia.org/wiki/Distributivgesetz">Distributivgesetz</a></li> <li><strong>Relationen</strong>: <a href="http://de.wikipedia.org/wiki/Injektivit%C3%A4t">Injektivit&auml;t</a>, <a href="http://de.wikipedia.org/wiki/Surjektivit%C3%A4t">Surjektivit&auml;t</a>, <a href="http://de.wikipedia.org/wiki/Bijektive_Funktion">Bijektivit&auml;t</a>, Linkstotalit&auml;t, Rechtseindeutigkeit, <a href="http://de.wikipedia.org/wiki/Reflexive_Relation">Reflexivit&auml;t</a>, <a href="http://de.wikipedia.org/wiki/Antisymmetrie">Antisymmetrie</a>, <a href="http://de.wikipedia.org/wiki/Symmetrische_Relation">Symmetrie</a>, <a href="http://de.wikipedia.org/wiki/Transitivit%C3%A4t_(Mathematik)">Transitivit&auml;t</a>, <a href="http://de.wikipedia.org/wiki/Ordnungsrelation">Ordnungsrelation</a>, <a href="http://de.wikipedia.org/wiki/%C3%84quivalenzrelation">&Auml;quivalenzrelation</a></li> <li><strong>Mengeneigenschaften</strong>: <a href="http://de.wikipedia.org/wiki/Abz%C3%A4hlbarkeit">Abz&auml;hlbarkeit</a>, <a href="http://de.wikipedia.org/wiki/%C3%9Cberabz%C3%A4hlbarkeit">&Uuml;berabz&auml;hlbarkeit</a>, endlich, unendlich, <a href="http://de.wikipedia.org/wiki/Beschr%C3%A4nktheit">Beschr&auml;nktheit</a></li> <li><strong>Folgeneigenschaften</strong>: <a href="http://de.wikipedia.org/wiki/Supremum">Supremum</a>, Infimum, Minimum, Maximum, Konvergenz, Divergenz, <a href="http://de.wikipedia.org/wiki/Grenzwert_(Folge)">Grenzwert</a>, Limes superior, Limes inferior, <a href="http://de.wikipedia.org/wiki/Monotonie_(Mathematik)">Monotonie</a></li> <li><a href="../wie-fuhre-ich-einen-induktionsbeweis/" title="Wie f&uuml;hre ich einen Induktionsbeweis?">Beweis durch vollst&auml;ndige Induktion</a></li> <li><a href="http://de.wikipedia.org/wiki/Teilfolge">Teilfolgen</a>, H&auml;ufungswerte</li> <li><a href="http://de.wikipedia.org/wiki/Reihe_(Mathematik)">Reihen</a>: Monotoniekriterium, Dreiecksungleichung</li> <li><a href="http://de.wikipedia.org/wiki/Umordnung_von_Reihen">Umordnungen</a> und Produktreihen</li> <li><a href="http://de.wikipedia.org/wiki/Potenzreihe">Potenzreihen</a>, <a href="http://de.wikipedia.org/wiki/Konvergenzradius">Konvergenzradius</a></li> <li>g-adische Entwicklungen</li> <li><strong>Funktionen</strong>: Grenzwerte, H&auml;ufungspunkte, <a href="http://de.wikipedia.org/wiki/Stetigkeit">Stetigkeit</a>, abgeschlossen, offen, <a href="http://de.wikipedia.org/wiki/Gleichm%C3%A4%C3%9Fige_Konvergenz">gleichm&auml;&szlig;ige Konvergenz</a>, <a href="http://de.wikipedia.org/wiki/Gleichm%C3%A4%C3%9Fige_Stetigkeit">gleichm&auml;&szlig;ige Stetigkeit</a>, <a href="http://de.wikipedia.org/wiki/Lipschitz-Stetigkeit">Lipschitz-Stetigkeit</a></li> </ul> <h4>S&auml;tze</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Satz_von_Bolzano-Weierstra%C3%9F">Satz von Bolzano-Weierstra&szlig;</a></li> <li><a href="http://de.wikipedia.org/wiki/Cauchy-Kriterium">Cauchy-Kriterium</a></li> <li><a href="http://de.wikipedia.org/wiki/Leibniz-Kriterium">Leibniz-Kriterium</a></li> <li><a href="http://de.wikipedia.org/wiki/Majorantenkriterium">Majorantenkriterium</a> und Minorantenkriterium</li> <li><a href="http://de.wikipedia.org/wiki/Wurzelkriterium">Wurzelkriterium</a></li> <li><a href="http://de.wikipedia.org/wiki/Quotientenkriterium">Quotientenkriterium</a></li> <li><a href="http://de.wikipedia.org/wiki/Riemannscher_Umordnungssatz">Riemannscher Umordnungssatz</a></li> </ul> <h4>Formeln</h4> <ul> <li>`$\binom{n}{k} + \binom{n}{k-1} = \binom{n+1}{k}$`</li> <li>`$a^{n+1} - b^{n+1} = (a - b) \sum_{k=0}^{n} a^{n-k} b^{k}$`</li> <li><a href="http://de.wikipedia.org/wiki/Bernoullische_Ungleichung">Bernoullische Ungleichung</a>: `$x \geq -1: (1+x)^n \geq 1 + nx ~ \forall n \in \mathbb{N}$`</li> <li><a href="http://de.wikipedia.org/wiki/Binomischer_Satz">Binomischer Lehrsatz</a>: `$(a+b)^n = \sum_{k=0}^{n} \binom{n}{k}a^{n-k} b^k ~ \forall n \in \mathbb{N}$`</li> </ul> <h4>Wichtige Grenzwerte</h4> <ul> <li>`$\sqrt[n\,]{n} \rightarrow 1 (n \rightarrow \infty)$`</li> <li>`$e = \lim_{n \to \infty} (1+\frac{1}{n})^n = \lim_{n \to \infty} \sum_{k=0}{n} \frac{1}{k!}$`</li> </ul> <h4>Wichtige Reihen</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Harmonische_Reihe">Harmonische Reihe</a>: `$\sum_{n=1}^\infty \frac{1}{n}$` (Divergent)</li> <li><a href="http://de.wikipedia.org/wiki/Geometrische_Reihe">Geometrische Reihe</a>: `$\sum_{n=0}^{\infty} x^n (x \in \mathbb{R})$`. Konvergiert, falls |x| &lt; 1 gegen `$\frac{1}{1-x}$`</li> <li><a href="http://de.wikipedia.org/wiki/Alternierende_Reihe">Alternierende Harmonische Reihe</a>: `$\sum_{n=1}^{\infty} (-1)^{n+1} \frac{1}{n}$`</li> <li>`$e^x = \sum_{n=0}{\infty} \frac{x^n}{x!}$`</li> <li>Kosinus: `$cos(x) = \sum_{n=0}{\infty} (-1)^n \cdot \frac{x^{2n}}{(2n)!} (x \in \mathbb{R})$`</li> <li>Sinus: `$sin(x) = \sum_{n=0}^{\infty} (-1)^n \cdot \frac{x^{2n+1}}{(2n+1)!} (x \in \mathbb{R}$`</li> <li>Cosinus Hyperbolikus: `$cosh(x) = \frac{1}{2} (e^x + e^{-x}) (x \in \mathbb{R})$`</li> <li>Sinus Hyperbolikus: `$sinh(x) = \frac{1}{2} (e^x - e^{-x}) (x \in \mathbb{R})$`</li> </ul> <h4>Links und Materialien</h4> <ul> <li><a href="http://mitschriebwiki.nomeata.de/Ana1Infos.html">Skript</a></li> <li><a href="http://ocw.mit.edu/courses/mathematics/18-100b-analysis-i-fall-2010/">MIT OpenCourseWare</a></li> </ul> <h3>Lineare Algebra</h3> <h4>Algebraische Strukturen</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Gruppentheorie">Gruppen</a>: <ul> <li><a href="http://de.wikipedia.org/wiki/Gruppentheorie#Definition">Definition</a></li> <li>Beispiele: alle Ringe und K&ouml;rper</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Ringtheorie">Ringe</a>: <ul> <li><a href="http://de.wikipedia.org/wiki/Ringtheorie#Ring">Definition</a></li> <li>Beispiele: alle K&ouml;rper</li> <li>Gegenbeispiele: `$(\mathbb{N}, +, \cdot)$`</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/K%C3%B6rper_(Algebra)">K&ouml;rper</a>: <ul> <li><a href="http://de.wikipedia.org/wiki/K%C3%B6rper_(Algebra)#Formale_Definition">Definition</a></li> <li>Beispiele: `$(\mathbb{Q}, +, \cdot), (\mathbb{R}, +, \cdot), (\mathbb{C}, +, \cdot), (\mathbb{Z}/p\mathbb{Z}, +, \cdot)$`</li> <li>Gegenbeispiele: `$(\mathbb{Z}, +, \cdot)$`</li> </ul> </li> <li><a href="http://de.wikipedia.org/wiki/Vektorraum">Vektorr&auml;ume</a>: <ul> <li><a href="http://de.wikipedia.org/wiki/Vektorraum#Formale_Definition">Definition</a></li> <li>Beispiele: `$\mathbb{R}^2, \mathbb{R}^3, ... , \mathbb{R}^n,$` Ring der Polynome</li> </ul> </li> </ul> <h4>Algorithmen</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Gau%C3%9Fsches_Eliminationsverfahren">Gau&szlig;sches Eliminationsverfahren</a>: <ul> <li>Was bedeuten Nullzeilen?</li> <li>Wann hat das LGS keine / eine / viele L&ouml;sungen?</li> <li>Welche Operationen erlaubt der Algorithmus?</li> </ul></li> <li><a href="http://de.wikipedia.org/wiki/Matrix_(Mathematik)#Matrizenmultiplikation">Matrixmultiplikation</a></li> </ul> <h4>Dies und das</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Permutation">Permutationen</a> und Transpositionen, <a href="http://de.wikipedia.org/wiki/Identische_Abbildung">Identische Abbildung</a></li> <li><a href="http://de.wikipedia.org/wiki/Direkte_Summe#Innere_direkte_Summe">Direkte Summe</a></li> <li><a href="../wie-bildet-man-den-schnitt-zweier-vektorraume/" title="Wie bildet man den Schnitt zweier Vektorr&auml;ume?">Schnitt zweier Vektorr&auml;ume berechnen</a></li> <li>Was bedeuten die folgenden Symbole: `$\subseteq, \subset, \subsetneq, \cup, \setminus, \cap, \emptyset$`</li> <li><a href="http://de.wikipedia.org/wiki/De_Morgan%E2%80%99sche_Gesetze">Regeln von de Morgan</a>: `$(A \cup B)^C = A^C \cap B^C$` und `$(A \cap B)^C = A^C \cup B^C$`</li> <li><a href="http://de.wikipedia.org/wiki/Homomorphismus">Homomorphismen</a>, <a href="http://de.wikipedia.org/wiki/Isomorphismus">Isomorphismen</a> (<a href="http://de.wikipedia.org/wiki/Automorphismus">Automorphismus</a>)</li> <li><a href="http://de.wikipedia.org/wiki/Charakteristik_(Mathematik)">Charakteristik</a>, <a href="http://de.wikipedia.org/wiki/Lineare_H%C3%BClle">Lineare H&uuml;lle</a>, <a href="http://de.wikipedia.org/wiki/Erzeugendensystem">Erzeugendensystem</a>, <a href="http://de.wikipedia.org/wiki/Basis_(Vektorraum)">Basis</a>, <a href="http://de.wikipedia.org/wiki/Standardbasis">Standardbasis</a>, <a href="http://de.wikipedia.org/wiki/Basiswechsel_(Vektorraum)">Basiswechsel</a></li> </ul> <h4>Links und Materialien</h4> <ul> <li><a href="http://ocw.mit.edu/courses/mathematics/18-06-linear-algebra-spring-2010/">MIT OpenCourseWare</a> (<a href="http://ocw.mit.edu/courses/mathematics/18-06-linear-algebra-spring-2010/video-lectures/">Video Lectures</a>)</li> </ul> <h3>Programmieren</h3> <p>Nur grundlagen in Java:</p> <ul> <li><a href="http://de.wikipedia.org/wiki/Objekt_(Programmierung)">Objekt</a></li> <li><a href="http://de.wikipedia.org/wiki/Klasse_(Programmierung)">Klasse</a></li> <li><a href="http://de.wikipedia.org/wiki/Instanz_(Informatik)">Instanz</a></li> <li><a href="http://de.wikipedia.org/wiki/Methode_(Programmierung)">Methode</a></li> <li><a href="http://de.wikipedia.org/wiki/Zugriffsfunktion">Getter und Setter</a></li> <li><a href="http://de.wikipedia.org/wiki/Rekursion">Rekursion</a></li> <li>Zugriffsmodifikatoren: public, protected, private</li> <li><a href="http://docs.oracle.com/javase/tutorial/java/IandI/abstract.html">abstract</a></li> <li><a href="http://de.wikipedia.org/wiki/Javadoc">Javadoc</a></li> <li><a href="http://de.wikibooks.org/wiki/Java_Standard:_Objekte#equals.28Object.29">.equals, .toString</a></li> </ul> <h3>Grundbegriffe der Informatik</h3> <h4>Aussagenlogik</h4> <ul> <li>Was bedeuten die folgenden Symbole: `$\Rightarrow, \Leftrightarrow, \neg, \land, \lor, \forall, \exists$`</li> </ul> <h4>Formale Sprachen</h4> <ul> <li>Wo ist der Unterschied zwischen `$\varepsilon$` und `$\emptyset$`?</li> <li><a href="http://de.wikipedia.org/wiki/Alphabet_(Informatik)">Alphabet</a>, <a href="http://de.wikipedia.org/wiki/Wort_(Theoretische_Informatik)">Wort</a>, <a href="http://de.wikipedia.org/wiki/Formale_Grammatik">Grammatik</a>, <a href="http://de.wikipedia.org/wiki/Formale_Sprache">Sprache</a></li> </ul> <h4>Graphen</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Gerichteter_Graph#Gerich">gerichtete</a>, ungerichtete und <a href="http://de.wikipedia.org/wiki/Graph_(Graphentheorie)#Gewichteter_Graph">gewichtete</a> <a href="http://de.wikipedia.org/wiki/Graph_(Graphentheorie)">Graphen</a></li> <li><a href="http://de.wikipedia.org/wiki/Baum_(Graphentheorie)">Baum</a>, <a href="http://de.wikipedia.org/wiki/Wurzel_(Graphentheorie)">Wurzel</a>, <a href="http://de.wikipedia.org/wiki/Bin%C3%A4rbaum">Bin&auml;rbaum</a></li> <li><a href="http://de.wikipedia.org/wiki/Glossar_Graphentheorie#Schleife">Schleife</a>, Schlinge, <a href="http://de.wikipedia.org/wiki/Glossar_Graphentheorie#Kreis">Kreis</a></li> </ul> <h4>Dies und das</h4> <ul> <li>Zusicherungen, <a href="http://de.wikipedia.org/wiki/Schleifeninvariante">Schleifeninvariante</a></li> <li><a href="http://de.wikipedia.org/wiki/Huffman-Codierung">Huffman-Codierung</a></li> <li><a href="http://de.wikipedia.org/wiki/Algorithmus_von_Floyd_und_Warshall">Algorithmus von Warshall</a>, <a href="http://de.wikipedia.org/wiki/Adjazenzmatrix#Adjazenzmatrix_.28Nachbarschaftsmatrix.29">Adjazenzmatrix</a></li> <li><a href="http://de.wikipedia.org/wiki/Landau-Symbole">Landau-Symbole</a>: `$\cal O, \Omega, \Theta$`</li> <li><a href="http://de.wikipedia.org/wiki/Mealy-Automat">Mealy-Automat</a> und <a href="http://de.wikipedia.org/wiki/Moore-Automat">Moore-Automat</a></li> </ul> <h2>3. Semester</h2> <h3>Betriebssysteme</h3> <h4>Dies und das</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/POSIX">POSIX</a></li> <li>policy and mechanism</li> <li><a href="http://en.wikipedia.org/wiki/Multiprogramming">multiprogramming</a> and <a href="http://en.wikipedia.org/wiki/Batch_system">Batch processing</a></li> <li><a href="http://en.wikipedia.org/wiki/Zombie_process">Zombie</a> and <a href="http://en.wikipedia.org/wiki/Orphan_process">Orphan</a>, <a href="http://en.wikipedia.org/wiki/Fork_(operating_system)">fork</a>, <a href="http://en.wikipedia.org/wiki/Fork_bomb">fork bomb</a></li> <li>Memory layout of a process (Stack, Heap, BSS, data, rodata, text)</li> <li>(synchroner / asynchroner) <a href="http://de.wikipedia.org/wiki/Interrupt">Interrupt</a>, Excaption, Trap, <a href="http://de.wikipedia.org/wiki/System_Call">System Call</a></li> </ul> <h4>Multithreaded Programming</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Deadlock">Deadlock</a></li> <li>Mutual exclusion, hold and wait, No preemption</li> <li><a href="http://de.wikipedia.org/wiki/Critical_Section">Critical section</a>, <a href="http://de.wikipedia.org/wiki/Semaphor_(Informatik)">semaphore</a>, <a href="http://de.wikipedia.org/wiki/Mutex">mutex</a>, binary semaphore</li> <li>Spinlock</li> <li>Progress, Bounded waiting</li> <li><a href="http://de.wikipedia.org/wiki/Race_Condition">Race Condition</a></li> </ul> <h4>Cache</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Cache">Cache</a> <li><a href="http://en.wikipedia.org/wiki/CPU_cache">CPU cache</a></li> <li><a href="http://de.wikipedia.org/wiki/Cache-Algorithmus#Write_Through_.28Write_Thru.29">Write through</a> und <a href="http://de.wikipedia.org/wiki/Cache-Algorithmus#Write_Back">write back</a> policy</li> <li><a href="http://de.wikipedia.org/wiki/Lokalit%C3%A4tseigenschaft">Lokalit&auml;tseigenschaft</a></li> <h4>Scheduling</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Prozess-Scheduler">scheduler</a></li> <li><a href="http://en.wikipedia.org/wiki/Gantt_chart">Gantt chart</a></li> <li>turnaround time, response time, waiting time</li> <li>Starvation</li> <li>hardware requirements of preemptitive scheduling</li> <li><a href="http://en.wikipedia.org/wiki/Scheduling_(computing)#Dispatcher">dispatcher</a></li> </ul> <h4>Memory Management</h4> <ul> <li>TLB: <a href="http://de.wikipedia.org/wiki/Translation_Lookaside_Buffer">Translation Lookaside Buffer</a></li> <li>Swapping: Roll out, Roll in</li> <li>Allocation</li> <li>Relocation</li> <li>Segmentation</li> <li><a href="http://en.wikipedia.org/wiki/Paging">Paging</a></li> <li>First-fit, Best-fit, Worst-fit</li> <li>External Fragmentation, Internal Fragmentation</li> <li>Compile Time, Load time, Execution time</li> <li>Segment table</li> </ul> <h3>Theoretische Grundlagen der Informatik</h3> <h4>Automaten</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Deterministischer_endlicher_Automat">DEA</a>: `$(Q, \Sigma, \delta: Q \times \Sigma \rightarrow Q, s \in Q, F \subseteq Q)$`</li> <li><a href="http://de.wikipedia.org/wiki/Nichtdeterministischer_endlicher_Automat">NEA</a>: `$(Q, \Sigma, \delta: Q \times \Sigma \rightarrow 2^Q, s \in Q, F \subseteq Q)$`, wobei `$2^Q$` die Potenzmenge von Q ist.</li> <li>&Auml;quivalenz von DEA und NEA sowie die <a href="../konstruktion-eines-deterministischen-endlichen-automaten-aus-einem-nicht-deterministischem/" title="Konstruktion eines deterministischen endlichen Automaten aus einem nicht-deterministischem">Konstruktion</a></li> <li><a href="http://de.wikipedia.org/wiki/Turingmaschine">Turingmaschine</a>: `$(Q, \Sigma, \square, \Gamma, s \in Q, \delta: Q \times \Gamma \rightarrow Q \times \Gamma \times \{L, R, N\}, F \subseteq Q)$`</li> <li><a href="http://de.wikipedia.org/wiki/Churchsche_These">Church'che These</a></li> <li><a href="http://de.wikipedia.org/wiki/Satz_von_Rice">Satz von Rice</a></li> <li>Orakelmodul, Orakelband und <a href="http://de.wikipedia.org/wiki/Orakel-Turingmaschine">Orakel-Turingmaschine</a></li> </ul> <h4>Sprachen und Probleme</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/Kleenescher_Abschluss">Kleene'scher Abschluss</a>: `$L^*$`</li> <li>Positiver Abschluss: `$L^+$`</li> <li>Produktsprache: `$L_1 \cdot L_2$`</li> <li>Komplementsprache: `$L^C := \Sigma^* \setminus L$`</li> <li><a href="http://de.wikipedia.org/wiki/Regul%C3%A4re_Sprache">Regul&auml;re Sprachen</a>: Alle von einem DEA erkannten Sprachen.</li> <li><a href="../pumping-lemma/" title="Beweis durch Widerspruch: Eine Sprache ist nicht regul&auml;r (Pumping-Lemma)">Pumping-Lemma</a></li> <li><a href="http://de.wikipedia.org/wiki/Nerode-Relation">Nerode-Relation</a></li> <li><a href="http://de.wikipedia.org/wiki/Entscheidbarkeit">Entscheidbarkeit</a>, <a href="http://de.wikipedia.org/wiki/Berechenbarkeit">Berechenbarkeit</a></li> <li><a href="http://de.wikipedia.org/wiki/Diagonalsprache">Diagonalsprache</a>, <a href="http://de.wikipedia.org/wiki/Halteproblem">Halteproblem</a>, Universelle Sprache, <a href="http://de.wikipedia.org/wiki/Post%27sches_Korrespondenzproblem">Postsches Korrespondenzproblem</a></li> <li>Entscheidungsprobleme, <a href="http://de.wikipedia.org/wiki/Optimierungsproblem">Optimalwertprobleme</a>, Optimierungsprobleme, Suchprobleme</li> <li><a href="http://de.wikipedia.org/wiki/Erf%C3%BCllbarkeitsproblem_der_Aussagenlogik">SAT</a>, <a href="http://de.wikipedia.org/wiki/Problem_des_Handlungsreisenden">TSP</a>, <a href="http://de.wikipedia.org/wiki/3-SAT">3-SAT</a>, <a href="http://de.wikipedia.org/wiki/Knoten%C3%BCberdeckungen,_Cliquen_und_stabile_Mengen">CLIQUE</a>, <a href="http://de.wikipedia.org/wiki/3COLOR">3COLOR</a>, <a href="http://de.wikipedia.org/wiki/Exact_Cover">EXACT COVER</a>, <a href="http://de.wikipedia.org/wiki/Subset_Sum">SUBSET SUM</a>, <a href="http://de.wikipedia.org/wiki/Partitionierungsproblem">PARTITION</a></li> <li>Approximationen, Approximationsg&uuml;te</li> </ul> <h4>Komplexit&auml;tsklassen</h4> <ul> <li><a href="http://de.wikipedia.org/wiki/P_(Komplexit%C3%A4tsklasse)">P</a> und co-P</li> <li><a href="http://de.wikipedia.org/wiki/NP_(Komplexit%C3%A4tsklasse)">NP</a> und <a href="http://de.wikipedia.org/wiki/Co-NP">co-NP</a></li> <li><a href="http://de.wikipedia.org/wiki/NP-Vollst%C3%A4ndigkeit">NPC</a> und <a href="http://de.wikipedia.org/wiki/Satz_von_Cook">Satz von Cook</a></li> <li><a href="http://de.wikipedia.org/wiki/P-NP-Problem">P vs. NP</a>: Wie k&ouml;nnte es bewiesen / wiederlegt werden?</li> <li>`$\cal NPI := NP \setminus (P \cup NPC)$`</li> <li><a href="http://de.wikipedia.org/wiki/NP-schwer">NP-schwer</a></li> </ul> <h3>Wahrscheinlichkeitstheorie</h3> Hier haben wir ja die "Wahrscheinlichkeitstheorie und Statistik f&uuml;r Studierende der Informatik und des Ingenieurwesens" von Prof. Dr. N. Henze und Priv.-Doz. Dr. D. Kadelka. Das haben wir vermutlich auch schon durchgearbeitet. Da dieses Skript sehr ausf&uuml;hrlich ist und in die Klausur mitgenommen werden darf, sehe ich eigentlich keinen Bedarf an weiteren Erkl&auml;rungen. Es ist allerdings sehr zu empfehlen, die 11 &Uuml;bungsbl&auml;tter im VAB (Vorlesungsarbeitsbereich, Passwortgesch&uuml;tzt unter studium.kit.edu) zu machen! </li></ul> Wie bildet man den Schnitt zweier Vektorräume? //martin-thoma.com/wie-bildet-man-den-schnitt-zweier-vektorraume/ Sun, 08 Jan 2012 20:27:37 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-bildet-man-den-schnitt-zweier-vektorraume <h2>Angaben</h2> <p>Gegeben sind zwei Untervektorräume des <code>$\mathbb{R}^4$</code>: <code>$U_1 := \left [\begin{pmatrix} 2 \\ 5 \\ 3 \\ 17 \end{pmatrix}, \begin{pmatrix} 1 \\ 2 \\ 3 \\ 4 \end{pmatrix}, \begin{pmatrix} 1 \\ 3 \\ 3 \\ 7 \end{pmatrix}, \begin{pmatrix} -1 \\ 1 \\ -1 \\ 1 \end{pmatrix} \right ]$</code></p> <p><code>$U_2 := \left [\begin{pmatrix} 0 \\ 0 \\ 4 \\ 2 \end{pmatrix}, \begin{pmatrix} 3 \\ 1 \\ 4 \\ 1 \end{pmatrix}, \begin{pmatrix} 2 \\ 7 \\ 1 \\ 8 \end{pmatrix}, \begin{pmatrix} 36 \\ 126 \\ 8 \\ 139 \end{pmatrix} \right ]$</code>.</p> <h2>Aufgabe</h2> <p>Finde eine Basis für <code>$U_1 \cap U_2$</code>.</p> <p>Zusatzaufgabe: Finde eine Basis für <code>$U_1 + U_2$</code>.</p> <h2>Basis finden</h2> <p>Will man eine möglichst einfache Basis, also ein minimales Erzeugendensystem mit möglichst kleinen Zahlen zu einem gegebenem Vektorraum finden, so kann man das <a href="http://de.wikipedia.org/wiki/Gau%C3%9Fsches_Eliminationsverfahren">Gaußsche Eliminationsverfahren</a> auf die erzeugenden Vektoren anwenden. Dazu transponiert man die Vektoren:</p> <p><code>$\left( \begin{array}{c c c c | c} 2 &amp; 5 &amp; 3 &amp; 17 &amp; 0\\ 1 &amp; 2 &amp; 3 &amp; 4 &amp; 0\\ 1 &amp; 3 &amp; 3 &amp; 7 &amp; 0\\ -1 &amp; 1 &amp;-1 &amp; 1 &amp; 0 \end{array} \right)$</code></p> <p>Da im Gaußsche Eliminationsverfahren nur das Vertauschen von Zeilen, die Multiplikation einer Zeile mit einer Konstanten und die Addition von Zeilen zugelassen sind, bleibt die rechte Spalte immer Null. Sie kann also weggelassen werden:</p> <p><code>$\left( \begin{array}{c c c c} 2 &amp; 5 &amp; 3 &amp; 17\\ 1 &amp; 2 &amp; 3 &amp; 4\\ 1 &amp; 3 &amp; 3 &amp; 7\\ -1 &amp; 1 &amp;-1 &amp; 1 \end{array} \right) \rightsquigarrow \left( \begin{array}{c c c c} 1 &amp;-1 &amp; 1 &amp;-1\\ 0 &amp; 3 &amp; 2 &amp; 5\\ 0 &amp; 4 &amp; 2 &amp; 8\\ 0 &amp; 7 &amp; 1 &amp; 19 \end{array} \right) \rightsquigarrow \left( \begin{array}{c c c c} 1 &amp;-1 &amp; 1 &amp;-1\\ 0 &amp; 1 &amp; \frac{1}{2} &amp; 2\\ 0 &amp; 0 &amp; \frac{1}{2} &amp; -1\\ 0 &amp; 0 &amp; -\frac{5}{2} &amp; 5 \end{array} \right) \rightsquigarrow $</code> <code>$\left( \begin{array}{c c c c} 1 &amp;-1 &amp; 1 &amp;-1\\ 0 &amp; 1 &amp; \frac{1}{2} &amp; 2\\ 0 &amp; 0 &amp; 1 &amp; -2\\ 0 &amp; 0 &amp; -5 &amp; 10 \end{array} \right) \rightsquigarrow \left( \begin{array}{c c c c} 1 &amp; 0 &amp; 0 &amp; 4\\ 0 &amp; 1 &amp; 0 &amp; 3\\ 0 &amp; 0 &amp; 1 &amp; -2\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{array} \right)$</code></p> <p>Die Basis für <code>$U_1$</code> ist also <code>$\left \{\begin{pmatrix} 1 \\ 0 \\ 0 \\ 4 \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 0 \\ 3 \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 1 \\ -2 \end{pmatrix} \right \}$</code></p> <p>Ich habe gerade keine Lust, das ganze für <code>$U_2$</code> noch vorzurechnen. Es kommt <code>$\left( \begin{array}{c c c c} 1 &amp; 0 &amp; 0 &amp; -\frac{29}{38}\\ 0 &amp; 1 &amp; 0 &amp; \frac{49}{38}\\ 0 &amp; 0 &amp; 1 &amp; \frac{1}{2}\\ 0 &amp; 0 &amp; 0 &amp; 0 \end{array} \right)$</code>heraus, siehe <a href="http://www.wolframalpha.com/input/?i=RowReduce%5B%7B%7B2%2C+7%2C+1%2C+8%7D%2C%7B3%2C+1%2C+4%2C+1%7D%2C%7B0%2C+0%2C+4%2C+2%7D%2C%7B36%2C+126%2C+8%2C+139%7D%7D%5D">Wolfram|Alpha</a>.</p> <p>Die Basis für <code>$U_2$</code> ist also <code>$\left \{\begin{pmatrix} 1 \\ 0 \\ 0 \\ -\frac{29}{38} \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 0 \\ \frac{49}{38} \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 1 \\ \frac{1}{2} \end{pmatrix} \right \}$</code></p> <h2>Zassenhaus-Algorithmus</h2> <p>Bemerkung: Ich habe für den Zassenhaus-Algorithmus leiter die falsche Basis genommen. Der Rechenfehler zieht sich bis zum Ende durch. Wenn ich mal Zeit habe, werde ich es korrigieren (Alternativ: Wenn es jemand von euch macht, kann er den TeX-Code ja als Kommentar bereitstellen).</p> <p>Man transponiert die Basisvektoren von <code>$U_1$</code> und <code>$U_2$</code> und schreibt sie in eine Matrix: <code>$\left( \begin{array}{c | c} U_1^T &amp; U_1^T \\ \hline U_2^T &amp; 0 \end{array} \right)$</code>.</p> <p>Natürlich nimmt man für <code>$U_1$</code> die einfachere der beiden Basen. Dann löst man das ganze wieder mit Gauß:</p> <p><code>$\left( \begin{array}{c c c c | c c c c} 1 &amp; 0 &amp; 0 &amp; 4 &amp; 1 &amp; 0 &amp; 0 &amp; 4 \\ 0 &amp; 1 &amp; 0 &amp; 3 &amp; 0 &amp; 1 &amp; 0 &amp; 3 \\ 0 &amp; 0 &amp; 1 &amp;-2 &amp; 0 &amp; 0 &amp; 1 &amp;-2 \\ \hline 1 &amp; 0 &amp; 0 &amp; - \frac{29}{38} &amp; 0 &amp; 0 &amp; 0 &amp; 0 \\ 0 &amp; 1 &amp; 0 &amp; \frac{49}{38} &amp; 0 &amp; 0 &amp; 0 &amp; 0 \\ 0 &amp; 0 &amp; 1 &amp; \frac{1}{38} &amp; 0 &amp; 0 &amp; 0 &amp; 0 \end{array} \right) \rightsquigarrow \left( \begin{array}{c c c c | c c c c} 1 &amp; 0 &amp; 0 &amp; 4 &amp; 1 &amp; 0 &amp; 0 &amp; 4 \\ 0 &amp; 1 &amp; 0 &amp; 3 &amp; 0 &amp; 1 &amp; 0 &amp; 3 \\ 0 &amp; 0 &amp; 1 &amp;-2 &amp; 0 &amp; 0 &amp; 1 &amp;-2 \\ \hline 0 &amp; 0 &amp; 0 &amp; - \frac{181}{38} &amp; -1 &amp; 0 &amp; 0 &amp; -4 \\ 0 &amp; 0 &amp; 0 &amp; - \frac{65}{38} &amp; 0 &amp; -1 &amp; 0 &amp; -3 \\ 0 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; - \frac{38}{75} &amp; \frac{76}{75} \end{array} \right) \rightsquigarrow $</code> <code>$\left( \begin{array}{c c c c | c c c c} 1 &amp; 0 &amp; 0 &amp; 4 &amp; 1 &amp; 0 &amp; 0 &amp; 4 \\ 0 &amp; 1 &amp; 0 &amp; 3 &amp; 0 &amp; 1 &amp; 0 &amp; 3 \\ 0 &amp; 0 &amp; 1 &amp;-2 &amp; 0 &amp; 0 &amp; 1 &amp;-2 \\ 0 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; - \frac{38}{75} &amp; \frac{76}{75} \\ \hline 0 &amp; 0 &amp; 0 &amp; 0 &amp; -1 &amp; 0 &amp; \frac{181}{75} &amp; \frac{62}{75} \\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0 &amp; -1 &amp; - \frac{13}{15} &amp; \frac{26}{15} \end{array} \right) \rightsquigarrow \left( \begin{array}{c c c c | c c c c} 1 &amp; 0 &amp; 0 &amp; 4 &amp; 1 &amp; 0 &amp; 0 &amp; 4 \\ 0 &amp; 1 &amp; 0 &amp; 3 &amp; 0 &amp; 1 &amp; 0 &amp; 3 \\ 0 &amp; 0 &amp; 1 &amp;-2 &amp; 0 &amp; 0 &amp; 1 &amp;-2 \\ 0 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; - \frac{38}{75} &amp; \frac{76}{75} \\ \hline 0 &amp; 0 &amp; 0 &amp; 0 &amp; -1 &amp; 0 &amp; 181 &amp; 62 \\ 0 &amp; 0 &amp; 0 &amp; 0 &amp; 0 &amp; 1 &amp; 13 &amp; - 26 \end{array} \right)$</code></p> <p>Rechts unten steht nun die Basis für <code>$U_1 \cap U_2 = \left [ \left \{ \begin{pmatrix} -1 \\ 0 \\ 181 \\ 62 \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 13 \\ -26 \end{pmatrix} \right \} \right ]$</code>. Zusätzlich steht links oben die Basis für <code>$U_1 + U_2$</code>. Wenn man das noch etwas umformt ist es die Standardbasis des <code>$\mathbb{R}^4$</code>.</p> <h2>Methode 2</h2> <h3>Angabe</h3> <p><code>$U_1 = \left [ \left \{\begin{pmatrix} 1 \\ 0 \\ 0 \\ 4 \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 0 \\ 3 \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 1 \\ -2 \end{pmatrix} \right \} \right ]$</code>,</p> <p><code>$U_2 = \left [ \left \{\begin{pmatrix} 1 \\ 0 \\ 0 \\ -\frac{29}{38} \end{pmatrix}, \begin{pmatrix} 0 \\ 1 \\ 0 \\ \frac{49}{38} \end{pmatrix}, \begin{pmatrix} 0 \\ 0 \\ 1 \\ \frac{1}{38} \end{pmatrix} \right \} \right ]$</code></p> <h3>Rechnung</h3> <p>Es gilt: <code>$x \in U_1 \cap U_2$</code> <code>$\Leftrightarrow x \in U_1 \land x \in U_2$</code> <code>$\Leftrightarrow x = a \cdot x_1 + b \cdot x_2 + c \cdot x_3 = d \cdot y_1 + e \cdot y_2 + f \cdot y_3$</code> mit <code>$a, b, c, d, e, f \in \mathbb{R}$</code>. <code>$\begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1\\ 4 &amp; 3 &amp; 2 &amp; -\frac{29}{38} &amp; \frac{49}{38} &amp; \frac{1}{38} \end{pmatrix} \rightsquigarrow \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; -\frac{181}{38} &amp; -\frac{65}{38} &amp; -\frac{75}{38} \end{pmatrix}$</code> <code>$\rightsquigarrow \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0\\ 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 1 &amp; \frac{65}{181} &amp; \frac{75}{181} \end{pmatrix} \rightsquigarrow \begin{pmatrix} 1 &amp; 0 &amp; 0 &amp; 0 &amp; -\frac{65}{181} &amp; -\frac{75}{181}\\ 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1 &amp; 0\\ 0 &amp; 0 &amp; 1 &amp; 0 &amp; 0 &amp; 1\\ 0 &amp; 0 &amp; 0 &amp; 1 &amp; \frac{65}{181} &amp; \frac{75}{181} \end{pmatrix}$</code></p> <p>Nun führt der -1 - Trick zu dieser Lösung: <code>$\mathcal{L} = \left [ \left \{ \begin{pmatrix} -\frac{65}{181} \\ 1 \\ 0 \\ \frac{65}{181} \\ -1 \\ 0\end{pmatrix}, \begin{pmatrix} -\frac{75}{181} \\ 0 \\ 1 \\ \frac{75}{181} \\ 0 \\ -1 \end{pmatrix} \right \} \right ] = \left [ \left \{ \begin{pmatrix} -65 \\ 181 \\ 0 \\ 65 \\ -181 \\ 0\end{pmatrix}, \begin{pmatrix} -75 \\ 0 \\ 181 \\ 75 \\ 0 \\ -181 \end{pmatrix} \right \} \right ]$</code></p> <p>Das ist also die Lösung für Belegungen von a, b, c, d, e, f, sodass der resultierende Vektor sowohl in <code>$U_1$</code>, als auch in <code>$U_2$</code> ist.</p> <p>Allerdings sieht es so aus, als hätte ich mich irgendwo verrechnet … Sieht jemand den Fehler?</p> <h2>Siehe auch</h2> <p><a href="http://werkzeuge.wieschoo.com/zassenalgo.php">Interaktiver Zassenhaus-Algorithmus</a></p> Frauenquote am KIT //martin-thoma.com/frauenquote-am-kit/ Sat, 07 Jan 2012 23:57:47 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/frauenquote-am-kit <p>Die Frauenquote am KIT wird oft genannt, allerdings hatte ich bisher nur grobe Zahlen. Nun habe ich eine <a href="http://www.kit.edu/downloads/Statistik_WS11.pdf">zuverlässige Quelle</a> mit Zahlen zum WS 2011/2012. Das ist die Frauenquote:</p> <p>Insgesamt: 26,6% (unter Deutschen: 25,3%; unter Ausländern: 33,5%)</p> <p>Fakultät für Architektur: 63,7 % Fakultät für Geisteswissenschaften: 62,2 % Fakultät für Chemie + Bio: 53,4 % Fakultät für Mathematik: 36,1 % Fakultät für Bauingenieur, Bio- und Umweltwissenschaften: 34,2 % Fakultät für Chemieingenieurwesen und Verfahrenstechnik: 30,1 % Fakultät für Wirtschaftswissenschaften: 23,9 % Fakultät für Informatik + Wirtschaftswissenschaften: 23,7 % Fakultät für Physik: 18,0 % Fakultät für Elektrotechnik und Informationstechnik: 10,9 % Fakultät für Maschinenbau: 10,6 % Fakultät für Informatik: 9,4 % Fakultät für Maschinenbau + Elektrotechnik und Informationstechnik: 8,7 % (diese Fakultät hat allerdings nur 23 Personen …)</p> <p>70,4 % der Studenten kommen übrigens aus Baden-Württemberg.</p> <h2>Siehe auch</h2> <p><a href="http://www.ka-news.de/region/karlsruhe/thema-des-monats./Mythos-Maennerstadt-Wie-maennlich-ist-Karlsruhe;art6066,793025">Mythos Männerstadt: Wie männlich ist Karlsruhe?</a></p> Wandering through the depths of find //martin-thoma.com/wandering-through-the-depths-of-find/ Wed, 28 Dec 2011 16:01:18 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wandering-through-the-depths-of-find <p>find is a very mighty tool. It allows you to apply a very detailed search syntax. Every Linux user should know how to use it.</p> <h2>Very basic usage</h2> <p><a href="../images/2011/09/find-basic1.png"><img src="../images/2011/09/find-basic1.png" alt="`$ find /home -iname &#039;Tux*&#039;" title="$` find /home -iname &#039;Tux*&#039;" width="500" height="100" class="alignnone size-full wp-image-2671" /></a></p> <p>I told you I would start with the very basics, didn’t I? So, you can need the option -iname if you want to do basic matching against the filename. The * can be used as a placeholder.</p> <h2>Redirecting errors</h2> <p>You might get some “Permission denied” errors. They are very bothersome if you combine commands in the bash. So you redirect them to /dev/null, a special file which discards everything it gets:</p> <p><a href="../images/2011/09/find-error-redirection.png"><img src="../images/2011/09/find-error-redirection.png" alt="find /home -iname &#039;Tux*&#039; 2&gt;/dev/null" title="find /home -iname &#039;Tux*&#039; 2&gt;/dev/null" width="500" height="100" class="alignnone size-full wp-image-2691" /></a></p> <h2>Real life example</h2> <p>I am also a developer who likes to have good names for constants, database tables and variables. Sometimes, like today, I think it’s time to change a database table a bit. It got a lot more rows and the old name doesn’t really fit any longer. I used a constant for the table name in all scripts. This constant was SOFTWARE_USER_TABLE and should now be USER_INFO_TABLE. So I have to search recursively and case-sensitive in my project and replace all occurences in all strings by the new string. Except for .svn-directories, of course. The easiest way to achieve this is via find, xargs and sed:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">find . -path <span class="s1">&#39;*/.svn&#39;</span> -prune -o -type f -print0 <span class="p">|</span> xargs -0 sed -i <span class="s1">&#39;s/SOFTWARE_USER_TABLE/USER_INFO_TABLE/g&#39;</span></code></pre></div> <p>Now the explanation of the different commands: <strong>find:</strong></p> <ul> <li>.: search in the current working directory</li> <li>-path '*/.svn' -prune': If a directory starting with .svn is in the path to the file, skip it</li> <li>-o: atlernative (OR)</li> <li>-type f: only search for files</li> <li>-print0: print the full file name on the standard output, followed by a null character (instead of the newline character that -print uses). This allows file names that contain newlines or other types of white space to be correctly interpreted by programs that process the find output. This option corresponds to the -0 option of xargs.</li> </ul> <p><strong>xargs</strong> -0: exchanges the arguments. -0 means that input items are terminated by a null character instead of by whitespace, and the quotes and backslash are not special (every character is taken lit erally). Disables the end of file string, which is treated like any other argument. Useful when input items might contain white space, quote marks, or backslashes. The GNU find -print0 option produces input suitable for this mode. <strong>sed:</strong></p> <ul> <li>-i: edit the given file in-place. If you would not use -i, it would just print everything in standard output</li> <li>/g: edit the file globaly. If you would not use g, sed would only replace the first occurence of SOFTWARE_USER_TABLE</li> </ul> <h2>Snippets</h2> <p>move all files in subdirectories to a single directory:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">find -type f -exec mv <span class="o">{}</span> collection/ <span class="se">\;</span></code></pre></div> <p>find all files which are bigger than 20MB and print their location and size. Maybe you could use du for this one, but I don’t know how:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">find / -type f -size +20000k -exec ls -lh <span class="o">{}</span> <span class="se">\;</span> 2&gt;/dev/null <span class="p">|</span> awk <span class="s1">&#39;{ print `$5 &quot;:\t&quot; $`8 }&#39;</span></code></pre></div> <p>find files in the home folder owned by alice:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">find /home -user alice</code></pre></div> <h2>Further reading</h2> <p>Note that you should use grep if you want to search for patterns in single files.</p> <ul> <li><a href="http://linux.die.net/man/1/find">man page</a></li> <li><a href="http://en.wikipedia.org/wiki/Find">Wikipedia</a></li> </ul> Surprising C errors //martin-thoma.com/surprising-c-errors/ Wed, 28 Dec 2011 15:18:43 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/surprising-c-errors <p>Those errors might be surprising and a good exercise for C beginners:</p> <h2>Empty printf</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;&quot;</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">error: zero-length gnu_printf format string</code></pre></div> <h2>Macros</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#define MY_MACRO printf(&quot;Hello World\n&quot;);</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="k">if</span> <span class="p">(</span><span class="mi">1</span><span class="p">)</span> <span class="n">MY_MACRO</span><span class="p">;</span> <span class="k">else</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Crazy, huh?</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">macro.c: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>main<span class="p">&amp;</span>rsquo<span class="p">;</span>: macro.c:8: error: <span class="p">&amp;</span>lsquo<span class="p">;</span><span class="k">else</span><span class="p">&amp;</span>rsquo<span class="p">;</span> without a previous <span class="p">&amp;</span>lsquo<span class="p">;</span><span class="k">if</span><span class="p">&amp;</span>rsquo<span class="p">;</span></code></pre></div> <h2>Single and Double quotes</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="err">&#39;</span><span class="n">hello</span><span class="p">,</span> <span class="n">world</span><span class="err">\</span><span class="n">n</span><span class="err">&#39;</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">macro.c:5:9: warning: character constant too long <span class="k">for</span> its <span class="nb">type</span> macro.c: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>main<span class="p">&amp;</span>rsquo<span class="p">;</span>: macro.c:5: warning: passing argument <span class="m">1</span> of <span class="p">&amp;</span>lsquo<span class="p">;</span><span class="nb">printf</span><span class="p">&amp;</span>rsquo<span class="p">;</span> makes pointer from integer without a cast /usr/include/stdio.h:339: note: expected <span class="p">&amp;</span>lsquo<span class="p">;</span>const char * __restrict__<span class="p">&amp;</span>rsquo<span class="p">;</span> but argument is of <span class="nb">type</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>int<span class="p">&amp;</span>rsquo<span class="p">;</span> macro.c:5: warning: format not a string literal and no format arguments</code></pre></div> <p>Thanks to <a href="http://www.drpaulcarter.com/cs/common-c-errors.php#3.1">drpaulcarter.com</a> for this example:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="k">const</span> <span class="kt">char</span> <span class="o">*</span> <span class="n">myPointer</span> <span class="o">=</span> <span class="sc">&#39;A&#39;</span><span class="p">;</span> <span class="p">(</span><span class="kt">void</span><span class="p">)</span> <span class="n">myPointer</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">macro.c: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>main<span class="p">&amp;</span>rsquo<span class="p">;</span>: macro.c:3: warning: initialization makes pointer from integer without a cast</code></pre></div> <h2>Pointers</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;string.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">char</span> <span class="o">*</span> <span class="n">myPointer</span><span class="p">;</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">myPointer</span><span class="p">,</span> <span class="s">&quot;Hello World!&quot;</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <div class="highlight"><pre><code class="language-bash" data-lang="bash">macro.c: In <span class="k">function</span> <span class="p">&amp;</span>lsquo<span class="p">;</span>main<span class="p">&amp;</span>rsquo<span class="p">;</span>: macro.c:7: warning: <span class="p">&amp;</span>lsquo<span class="p">;</span>myPointer<span class="p">&amp;</span>rsquo<span class="p">;</span> is used uninitialized in this <span class="k">function</span></code></pre></div> <h2>Loops</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">int</span> <span class="n">x</span> <span class="o">=</span> <span class="mi">42</span><span class="p">;</span> <span class="k">while</span><span class="p">(</span> <span class="n">x</span> <span class="o">&gt;</span> <span class="mi">0</span> <span class="p">);</span> <span class="n">x</span><span class="o">--</span><span class="p">;</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>No compiler error, but an infinite loop.</p> <h2>Null terminator of Strings</h2> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="cp">#include &lt;stdlib.h&gt;</span> <span class="cp">#include &lt;string.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="kt">char</span> <span class="n">myArray</span><span class="p">[</span><span class="mi">20</span><span class="p">];</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Characters: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">myArray</span><span class="p">));</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">myArray</span><span class="p">,</span> <span class="s">&quot;abc&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Characters: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">myArray</span><span class="p">));</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">myArray</span><span class="p">,</span> <span class="s">&quot;Hello World!&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Characters: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">myArray</span><span class="p">));</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;String: -%s-</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">myArray</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Size: %i Byte</span><span class="se">\n\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="n">myArray</span><span class="p">));</span> <span class="kt">char</span> <span class="o">*</span> <span class="n">myString</span> <span class="o">=</span> <span class="n">malloc</span><span class="p">(</span><span class="n">strlen</span><span class="p">(</span><span class="n">myArray</span><span class="p">));</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">myString</span><span class="p">,</span> <span class="n">myArray</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;String: -%s-</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">myString</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Size: %i Byte</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="n">myString</span><span class="p">));</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Characters: %i</span><span class="se">\n\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">myString</span><span class="p">));</span> <span class="kt">char</span> <span class="o">*</span> <span class="n">breakIt</span> <span class="o">=</span> <span class="n">malloc</span><span class="p">(</span><span class="n">strlen</span><span class="p">(</span><span class="n">myString</span><span class="p">));</span> <span class="n">strcpy</span><span class="p">(</span><span class="n">breakIt</span><span class="p">,</span> <span class="n">myString</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;String: -%s-</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">breakIt</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Size: %i Byte</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="k">sizeof</span><span class="p">(</span><span class="n">breakIt</span><span class="p">));</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;Characters: %i</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="n">strlen</span><span class="p">(</span><span class="n">breakIt</span><span class="p">));</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>Again, you don’t get a compiler error, but some strange results:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Characters: 0 Characters: 3 Characters: 12 String: -Hello World!- Size: <span class="m">20</span> Byte String: -Hello World!- Size: <span class="m">4</span> Byte Characters: 12 String: -Hello World!- Size: <span class="m">4</span> Byte Characters: 13</code></pre></div> <h2>Further reading</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/C_preprocessor">C Preprocessor</a> and <a href="http://en.wikipedia.org/wiki/C_preprocessor#Macro_definition_and_expansion">macros</a></li> <li><a href="http://www.drpaulcarter.com/cs/common-c-errors.php#2.8">Pointer initialisation</a></li> <li><a href="http://linux.die.net/man/3/strcpy">strcpy</a>, <a href="http://linux.die.net/man/3/strlen">strlen</a></li> </ul> What seems to be wrong in the U.S. - some caricatures //martin-thoma.com/what-seems-to-be-wrong-in-the-u-s-some-caricatures/ Wed, 28 Dec 2011 14:23:30 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/what-seems-to-be-wrong-in-the-u-s-some-caricatures <p>I am not the first person you should ask if you want to know something about the United States. I’ve never been there and I know only one American. But I am reading quite a lot of websites which publish regularly political caricatures. This post is simply a collection of different caricatures I’ve stumbled over. For most of them I had to search the source, so I hope you will enjoy them.</p> <p>If you are the owner of one of these websites and don’t want me to publish your caricatures, I’ll remove them. But I will also remove the link to your website.</p> <h2>We are the 99%</h2> <p><a href="http://en.wikipedia.org/wiki/We_are_the_99%25">We are the 99%</a> is a political slogan of “Occupy” protesters. It refers to the vast concentration of wealth among the top 1% of income earners compared to the other 99%, and indicates that most people are paying the price for the mistakes of a tiny minority.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/99-percent-300x217.jpg"><img src="../images/2011/12/99-percent-300x217.jpg" alt="We are the 99% - Caricature from mattbors.com" width="" height="" class="size-medium wp-image-10371 " /></a><p class="wp-caption-text">We are the 99% - Caricature from mattbors.com</p></div> <p>(mattbors.com has some more caricatures from the occupy protesters)</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/wall-street-demonstrators-bankers-300x227.jpg"><img src="../images/2011/12/wall-street-demonstrators-bankers-300x227.jpg" alt="Wall Street - Demonstrators vs. Bankers" width="" height="" class="size-medium wp-image-10391" /></a><p class="wp-caption-text">Wall Street - Demonstrators vs. Bankers (from&nbsp;&lt;a href=http://www.startribune.com/opinion/131177628.html&gt;Startribune.com)</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/dessert-american-style-300x225.jpg"><img src="../images/2011/12/dessert-american-style-300x225.jpg" alt="Dessert - the american style (from David Horsey)" width="" height="" class="size-medium wp-image-10441" /></a><p class="wp-caption-text">Dessert - the american style (from &lt;a href=http://blog.seattlepi.com/davidhorsey/2011/09/19/how-we-slice-the-pie-in-the-usa/&gt;David Horsey)</p></div> <p>Some of the best caricatures are made by <a href="http://en.wikipedia.org/wiki/David_Horsey">David Horsey</a>.</p> <h2>Republicans</h2> <p>The <a href="http://en.wikipedia.org/wiki/Republican_Party_(United_States)">Republican Party</a> is one of the two major contemporary political parties in the United States, along with the Democratic Party. Founded by anti-slavery expansion activists in 1854, it is often called the GOP (Grand Old Party). The party’s platform generally reflects American conservatism in the U.S. political spectrum and is considered center-right, in contrast to the center-left Democratic Party.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/republicans-big-government-300x249.jpg"><img src="../images/2011/12/republicans-big-government-300x249.jpg" alt="The Principled Pachyderm (from M. Wuerker)" width="" height="" class="size-medium wp-image-10501" /></a><p class="wp-caption-text">The Principled Pachyderm (from &lt;a href=http://www.politico.com/wuerker/archive/20111201-the-principled-pachyderm.html&gt;M. Wuerker)</p></div> <h2>Tea Party</h2> <p>The <a href="http://en.wikipedia.org/wiki/Tea_Party_movement">Tea Party movement</a> is an American populist political movement that is generally recognized as conservative and libertarian, and has sponsored protests and supported political candidates since 2009. It endorses reduced government spending, opposition to taxation in varying degrees, reduction of the national debt and federal budget deficit, and adherence to an originalist interpretation of the United States Constitution.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/tea-party-big-government-300x219.jpg"><img src="../images/2011/12/tea-party-big-government-300x219.jpg" alt="Tea Party and big gouvernment" width="" height="" class="size-medium wp-image-10491" /></a><p class="wp-caption-text">Tea Party and big gouvernment</p></div> <p>Phil Hands has also made a nice one, but I’ve only found a page which clearly states “pay per use”. What a pity!</p> <p>I’ve just found the category tea party of <a href="http://theweek.com/section/cartoon/19/220783/the-tea-party">theweek.com</a>.</p> <h2>Education</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/education-africa-china-usa-300x181.jpg"><img src="../images/2011/12/education-africa-china-usa-300x181.jpg" alt="Education in China, Africa and the U.S. (from inconsequentiallogic.com)" width="" height="" class="size-medium wp-image-10561" /></a><p class="wp-caption-text">Education in China, Africa and the U.S. (from &lt;a href=http://www.inconsequentiallogic.com/2009/11/reality-can-bite.html&gt;inconsequentiallogic.com)</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/large-university-student-debt-us-300x225.jpg"><img src="../images/2011/12/large-university-student-debt-us-300x225.jpg" alt="University student dept (By Jeff Parker &copy; 2006 Florida Today)" width="" height="" class="size-medium wp-image-10571" /></a><p class="wp-caption-text">University student dept (By Jeff Parker &copy; 2006 Florida Today)</p></div> <h2>National debt</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/national-debt-trillion-caricature-jeff-parker-300x235.jpg"><img src="../images/2011/12/national-debt-trillion-caricature-jeff-parker-300x235.jpg" alt="National dept (from flatoday.net)" width="" height="" class="size-medium wp-image-10591" /></a><p class="wp-caption-text">National dept (from &lt;a href=http://jeffparker.flatoday.net/2009/11/1120-cartoon-debt-flood.shtml&gt;flatoday.net)</p></div> <p>I was very astonished that I did not find much about torture (e.g. <a href="http://en.wikipedia.org/wiki/Waterboarding">waterboarding</a>), human and civil rights (e.g. <a href="http://en.wikipedia.org/wiki/Guantanamo_Bay_detention_camp">Guantanamo Bay</a>, <a href="http://en.wikipedia.org/wiki/Capital_punishment_in_the_United_States">death penalty</a>) and the widespread ownership of arms (see <a href="http://en.wikipedia.org/wiki/Second_Amendment_to_the_United_States_Constitution">2nd Amendment</a>, <a href="http://en.wikipedia.org/wiki/List_of_countries_by_intentional_homicide_rate">List of countries by intentional homicide rate</a>).</p> <p>Do you know some good sites with caricatures? What do you think are the problems of Europe / Germany?</p> Adding a ppa in Ubuntu //martin-thoma.com/adding-a-ppa-in-ubuntu/ Sat, 24 Dec 2011 15:30:06 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/adding-a-ppa-in-ubuntu <p>PPAs (<a href="http://en.wikipedia.org/wiki/Personal_Package_Archive">Personal Package Archive</a>) provide additional resources. They are small repositories you can add to get some special content.</p> <p>You can add them with Bash:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo add-apt-repository ppa:&lt;repository-name&gt;</code></pre></div> <p>Lets make an example:</p> <p>If you want to install <a href="http://clipgrab.de/en">Clipgrab</a>, you add the repository first:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo add-apt-repository ppa:clipgrab</code></pre></div> <p>Then you have to update your sources:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get update</code></pre></div> <p>Now you can install clipgrab the usual way:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install clipgrab</code></pre></div> <h2>Further Reading</h2> <ul> <li><a href="https://help.ubuntu.com/community/Repositories/CommandLine">Repositories and the CommandLine</a></li> <li><a href="http://wiki.ubuntuusers.de/Clipgrab">Clipgrab</a> (German)</li> </ul> vrms - virtual Richard M. Stallman //martin-thoma.com/vrms-virtual-richard-m-stallman/ Fri, 23 Dec 2011 01:38:37 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/vrms-virtual-richard-m-stallman <div style="width: 210px" class="wp-caption alignright"><a href="../images/2011/12/Richard-Stallman-200x300.jpg"><img src="../images/2011/12/Richard-Stallman-200x300.jpg" alt="Richard Stallman" width="" height="" class="size-medium wp-image-10141 " /></a><p class="wp-caption-text">Richard Stallman</p></div> <p>I’ve just installed vrms - the virtual richard stallman :D</p> <p><a href="http://en.wikipedia.org/wiki/Richard_Stallman">Richard Stallman</a> is an American software freedom activist and computer programmer. He launched the GNU Project to create a free Unix-like operating system, and he has been the project’s lead architect and organizer. With the launch of the GNU Project, he initiated the free software movement; he founded the Free Software Foundation.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">$ </span>vrms Non-free packages installed on pc07 rar Archiver <span class="k">for</span> .rar files selfhtml German HTML reference and tutorial unrar Unarchiver <span class="k">for</span> .rar files <span class="o">(</span>non-free version<span class="o">)</span> Contrib packages installed on pc07 nvidia-common Find obsolete NVIDIA drivers ttf-mscorefonts-installer Installer <span class="k">for</span> Microsoft TrueType core fonts <span class="m">3</span> non-free packages, 0.2% of <span class="m">1869</span> installed packages. <span class="m">2</span> contrib packages, 0.1% of <span class="m">1869</span> installed packages.</code></pre></div> <p>Thanks to <a href="http://trompetenkaefer.wordpress.com/">trompetenkaefers blog</a> for the post!</p> How to use magic rescue //martin-thoma.com/how-to-use-magic-rescue/ Sat, 17 Dec 2011 13:02:47 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-use-magic-rescue <p>I’ve just searched an image I have created some time ago. I knew that I’ve put it on one of my USB-Sticks, but it seems as if I had deleted it. So how could I get the image back? Magic rescue is a program for recovering deleted files. It doesn’t simply open your trash can, but it searches files which were deleted, but not overwritten.</p> <h2>Installation</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install magicrescue</code></pre></div> <h2>Basic usage</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="sb">`</span><span class="nv">$ </span>magicrescue Usage: magicrescue <span class="o">[</span>-I FILE<span class="o">]</span> <span class="o">[</span>-M MODE<span class="o">]</span> <span class="o">[</span>-O <span class="o">[</span>+-<span class="o">=][</span>0x<span class="o">]</span>OFFSET<span class="o">]</span> <span class="o">[</span>-b BLOCKSIZE<span class="o">]</span> -d OUTPUT_DIR -r RECIPE1 <span class="o">[</span>-r RECIPE2 <span class="o">[</span>...<span class="o">]]</span> DEVICE1 <span class="o">[</span>DEVICE2 <span class="o">[</span>...<span class="o">]]</span> -b Only consider files starting at a multiple of BLOCKSIZE. -d Mandatory. Output directory <span class="k">for</span> found files. -r Mandatory. Recipe name, file or directory. -I Read input file names from this file <span class="o">(</span><span class="s2">&quot;-&quot;</span> <span class="k">for</span> stdin<span class="o">)</span> -M Produce machine-readable output to stdout. -O Resume from specified offset <span class="o">(</span>hex or decimal<span class="o">)</span> in the first device.</code></pre></div> <p>You need recipes to use Magic Rescue. These are the basic ones:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:/usr/share/magicrescue/recipes<span class="nv">$`</span> ls avi flac gzip mp3-id3v1 nikon-raw ppm canon-cr2 gimp-xcf jpeg-exif mp3-id3v2 perl zip elf gpl jpeg-jfif msoffice png</code></pre></div> <h2>Where is my USB-Stick?</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">$ </span>sudo fdisk -l <span class="o">[</span>sudo<span class="o">]</span> password <span class="k">for</span> moose: Disk /dev/sda: 320.1 GB, <span class="m">320072933376</span> bytes <span class="m">255</span> heads, <span class="m">63</span> sectors/track, <span class="m">38913</span> cylinders <span class="nv">Units</span> <span class="o">=</span> cylinders of <span class="m">16065</span> * <span class="nv">512</span> <span class="o">=</span> <span class="m">8225280</span> bytes Sector size <span class="o">(</span>logical/physical<span class="o">)</span>: <span class="m">512</span> bytes / <span class="m">512</span> bytes I/O size <span class="o">(</span>minimum/optimal<span class="o">)</span>: <span class="m">512</span> bytes / <span class="m">512</span> bytes Disk identifier: 0x00065e10 Device Boot Start End Blocks Id System /dev/sda1 * <span class="m">1</span> <span class="m">37810</span> <span class="m">303704064</span> <span class="m">83</span> Linux /dev/sda2 <span class="m">37810</span> <span class="m">38914</span> <span class="m">8864769</span> <span class="m">5</span> Extended /dev/sda5 <span class="m">37810</span> <span class="m">38914</span> <span class="m">8864768</span> <span class="m">82</span> Linux swap / Solaris Disk /dev/sdc: <span class="m">2067</span> MB, <span class="m">2067267584</span> bytes <span class="m">2</span> heads, <span class="m">63</span> sectors/track, <span class="m">32044</span> cylinders <span class="nv">Units</span> <span class="o">=</span> cylinders of <span class="m">126</span> * <span class="nv">512</span> <span class="o">=</span> <span class="m">64512</span> bytes Sector size <span class="o">(</span>logical/physical<span class="o">)</span>: <span class="m">512</span> bytes / <span class="m">512</span> bytes I/O size <span class="o">(</span>minimum/optimal<span class="o">)</span>: <span class="m">512</span> bytes / <span class="m">512</span> bytes Disk identifier: 0x005f4d47 Device Boot Start End Blocks Id System /dev/sdc1 * <span class="m">1</span> <span class="m">32045</span> <span class="m">2018800</span> b W95 FAT32</code></pre></div> <h2>Usage</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo magicrescue -r png -r jpeg-jfif -r gimp-xcf <span class="se">\</span> -r jpeg-exif -d /home/moose/output/ /dev/sdc1</code></pre></div> <p>Just got the image back ☺</p> Comparing programming languages //martin-thoma.com/comparing-programming-languages/ Sun, 11 Dec 2011 11:50:59 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/comparing-programming-languages <div style="width: 138px" class="wp-caption alignright"><a href="../images/2011/12/compare-programming-languages.png"><img src="../images/2011/12/compare-programming-languages.png" alt="Compare programming languages" width="" height="" class="size-full wp-image-9801 " /></a><p class="wp-caption-text">Compare programming languages</p></div> <p>If you want to compare programming languages, I can recommend the following links:</p> <ul> <li><a href="http://en.literateprograms.org/">literateprograms.org</a>, </li> <li><a href="http://rosettacode.org/wiki/Rosetta_Code">Rosetta Code</a>, </li> <li><a href="http://www.99-bottles-of-beer.net/abc.html">99-bottles-of-beer.net</a>,</li> <li><a href="http://en.wikipedia.org/wiki/Comparison_of_programming_languages_(basic_instructions)">Comparison of programming languages (basic instructions)</a>, </li> <li><a href="http://en.wikipedia.org/wiki/Comparison_of_programming_languages">Comparison of programming languages</a></li> </ul> <p>In particular, I like the following pages:</p> <ul> <li>Fibonacci numbers (<a href="http://en.literateprograms.org/Fibonacci_numbers_%28Python%29">literateprograms</a>, <a href="http://rosettacode.org/wiki/Fibonacci_sequence">rosettacode</a>)</li> <li>Hello World (<a href="http://en.literateprograms.org/Hello_World_%28Python%29">literateprograms</a>, <a href="http://rosettacode.org/wiki/Hello_world">rosettacode</a>)</li> </ul> <p>If you want to learn a new language you can look at the implementation of one problem and learn how the new language can be used.</p> OpenID autodiscovery //martin-thoma.com/openid-autodiscovery/ Sat, 10 Dec 2011 11:08:56 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/openid-autodiscovery <p><a href="../5-web-technologies-which-should-be-used-more-often/#OpenID">OpenID</a> is a web technology that gives the users the possibility to use one website for authentification on another web service. The <em>OpenID Attribute Exchange</em> makes registration processes simpler, as the user can automatically allow the website to get some information like the e-mail adress, the gender and the full name.</p> <p>The next step to an even simpler login process would be autodiscovery. This means there would be no need to do anything for logging in. You simply have to go to the website and be logged at your OpenID provider (e.g. Google). This is quite easily possible if the user was logged in before. You leave a cookie that gives you the information which OpenID he uses. So you simply don’t let him logout. I don’t know if it is a good idea to do so.</p> <p>The registration process is much trickier. Due to the <a href="http://en.wikipedia.org/wiki/Same_origin_policy">same origin policy</a>, you can’t read other cookies than those you have set. So you can’t check if there is a cookie from Google, Facebook or Yahoo.<br /> You could try if the user has a Google account, as Google uses a discovery URL (https://www.google.com/accounts/o8/id) instead of the usual OpenID (something like https://me.yahoo.com/martinthoma). So, by chance you will be able to let a user register without forcing him to interact in any way with your website. He has to allow your website to get his data at his OpenID provider, though.</p> <h2>Futher reading</h2> <ul> <li>Wikipedia: <ul> <li><a href="http://en.wikipedia.org/wiki/OpenID">OpenID</a>: an open standard that describes how users can be authenticated in a decentralized manner, eliminating the need for services to provide their own ad hoc systems and allowing users to consolidate their digital identities</li> <li><a href="http://en.wikipedia.org/wiki/Yadis">Yadis</a>: a communications protocol for discovery of services such as OpenID, OAuth, and XDI connected to a Yadis ID</li> </ul> </li> <li><a href="http://openid.net/specs/openid-attribute-exchange-1_0.html">OpenID Attribute Exchange 1.0</a>: Specification</li> <li><a href="https://docs.google.com/document/pub?id=1O7jyQLb7dW6EnJrFsWZDyh0Yq0aFJU5UJ4i5QzYlTjU&amp;pli=1">Guide to Running a User Account System</a>: by Eric Sachs of Google&rsquo;s Identity team</li> </ul> Configurig gEdit for developers //martin-thoma.com/configurig-gedit-for-developers/ Thu, 08 Dec 2011 23:10:19 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/configurig-gedit-for-developers <p><a href="http://en.wikipedia.org/wiki/Gedit">gedit</a> is a very lightweight text editor. It supports syntax highlighting for every programming language I can think of and is highly customizable.</p> <p>It belongs to GNOME, but it is also available for Windows. This is how it looks like:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/gedit-screenshot-300x208.png"><img src="../images/2011/12/gedit-screenshot-300x208.png" alt="gedit screenshot" width="" height="" class="size-medium wp-image-9571" /></a><p class="wp-caption-text">gedit screenshot</p></div> <p>You might want to install gedit-plugins:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install gedit-plugins</code></pre></div> <h2>External Tools</h2> <p>gedit allows you to run external command line tools by pressing shortcuts. You can find the external tools plugins in your preferences:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/gedit-external-tools1-300x209.png"><img src="../images/2011/12/gedit-external-tools1-300x209.png" alt="gedit external tools" width="" height="" class="size-medium wp-image-9601" /></a><p class="wp-caption-text">gedit external tools</p></div> <p>You can assign shortcuts by clicking into an input field and simply using the shortcut once:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/12/external-tool-java-300x209.png"><img src="../images/2011/12/external-tool-java-300x209.png" alt="external tools java" width="" height="" class="size-medium wp-image-9611" /></a><p class="wp-caption-text">external tools java</p></div> <h3>Java</h3> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="c">#!/bin/sh</span> <span class="nb">cd</span> <span class="sb">`</span><span class="nv">$GEDIT_CURRENT_DOCUMENT_DIR</span> <span class="k">if</span> javac <span class="nv">$`</span>GEDIT_CURRENT_DOCUMENT_NAME<span class="p">;</span> <span class="k">then</span> java <span class="k">${</span><span class="nv">GEDIT_CURRENT_DOCUMENT_NAME</span><span class="p">%\.java</span><span class="k">}</span> <span class="k">else</span> <span class="nb">echo</span> <span class="s2">&quot;Failed to compile&quot;</span> <span class="k">fi</span></code></pre></div> <h2>Code Comment</h2> <p>This neat little plugin detects which programming language you are using. If you select a code block and press ctrl+m it gets marked as a comment. If you press ctrl+shift+m a block of comments gets “decommented” to a block of code. It uses # for Python and // for Java.</p> <h2>Bracket Completion</h2> <p>Well, I guess the name is meaningful, isn’t it? As soon as you type a bracket - (, [ or { it gets completed with }, ] or ).</p> <h2>Better Python Console</h2> <p>The <a href="http://live.gnome.org/Gedit/Plugins/BetterPythonConsole">Better Python Console Plugin</a> allows you to press F5 and execute the current code in an interactive Python console. This means, you can access the current variables!</p> <p>You install it by extracting and copying the whole folder (with plugins!) to ~/gnome2/gedit.</p> <h2>What could be better</h2> <p>The design could be simmilar to Chrome ☺ So they could have some nicer tabs. Nothing really important.</p> <p>I really miss comment folding since I have to write Java code with a lot of Doc comments</p> <h2>Further reading and ressources</h2> <ul> <li><a href="http://projects.gnome.org/gedit/">Official Website</a>: You can find the Windows Binary here.</li> <li><a href="http://live.gnome.org/Gedit/ExternalToolsPluginCommands">External Tools</a></li> <li><a href="http://www.makeuseof.com/tag/top-plugins-to-extend-and-make-gedit-a-more-useful-text-editor-linux/">13 Gedit Plugins to Make It a More Useful Text Editor</a>: Seems as if you could also have a class browser in gedit</li> </ul> for loops in different programming languages //martin-thoma.com/for-loops-in-different-programming-languages/ Sun, 04 Dec 2011 11:19:54 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/for-loops-in-different-programming-languages <p>If you have to learn a new programming language it is most of the time quite easy. You know the structures and the way you have to think if you want to solve a problem. The first time it might be hard, but the more languages you learn the more simmilarities you’ll recognize.</p> <p>I also have to learn a special variant of <a href="http://en.wikipedia.org/wiki/Pseudocode">pseudocode</a> at the moment. It is quite hard to know what pseudocode does if it isn’t unambiguously defined. I had problems with for loops for example.</p> <p>For loops have some properties you simply have to define:</p> <ul> <li><strong>Scoping</strong>: Does the loop counter still exist after the loop was executed?</li> <li><strong>Copy or reference</strong>: Does the loop statement work with a copy or with a reference of the variables in the loop body?</li> <li><strong>Last value of i</strong>: What is the last value of i?</li> </ul> <h2>General structure</h2> <p>A for loop usually consists of an initialisation part, a condition and an interation step:</p> <div style="width: 295px" class="wp-caption aligncenter"><a href="../images/2011/11/for-loop-structure1.png"><img src="../images/2011/11/for-loop-structure1.png" alt="for loop structure" width="" height="" class="size-full wp-image-9251" /></a><p class="wp-caption-text">The structure of a for loop.</p></div> <h2>Pythons special strutcure</h2> <p>Python uses a generator or lists to loop:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">10</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;In loop: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">i</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;Out of loop: </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="n">i</span><span class="p">)</span></code></pre></div> <h2>Scoping</h2> <p>Does the loop counter still exist after the loop was executed?</p> <ul> <li><strong>Yes</strong>: JavaScript, PHP, Python</li> <li><strong>No</strong>: C, C++, Java</li> </ul> <h2>Copy or reference</h2> <p>Does the loop statement work with a copy or with a reference of the variables in the loop body? Does the programming language use the same variable as in the for condition (reference) or does it use another one (copy)? You can test this if you add something to i in the body.</p> <ul> <li><strong>Copy</strong>: Python</li> <li><strong>Reference</strong>: C, C++, Java, JavaScript, PHP</li> </ul> <p>Python iterates over a generator. This means that you can’t really compare Pythons for-loop to other programming languages’ for loops.</p> <h2>Last value of i</h2> <p>What is the last value of i?</p> <p><strong>9</strong>: C, C++, Java (Inside the loop), Python (Outside of the loop) <strong>10</strong>: JavaScript, PHP (Outside of the loop)</p> <h2>foreach</h2> <p>Many languages provide a special for loop. This special for loop is sometimes called “foreach” as you iterate over each element in a collection (e.g. an array).</p> <h3>Java</h3> <div class="highlight"><pre><code class="language-java" data-lang="java"><span class="kt">int</span><span class="o">[]</span> <span class="n">array</span> <span class="o">=</span> <span class="k">new</span> <span class="kt">int</span><span class="o">[</span><span class="mi">5</span><span class="o">];</span> <span class="n">array</span><span class="o">[</span><span class="mi">0</span><span class="o">]</span> <span class="o">=</span> <span class="mi">0</span><span class="o">;</span> <span class="n">array</span><span class="o">[</span><span class="mi">1</span><span class="o">]</span> <span class="o">=</span> <span class="mi">1</span><span class="o">;</span> <span class="n">array</span><span class="o">[</span><span class="mi">2</span><span class="o">]</span> <span class="o">=</span> <span class="mi">2</span><span class="o">;</span> <span class="n">array</span><span class="o">[</span><span class="mi">3</span><span class="o">]</span> <span class="o">=</span> <span class="mi">3</span><span class="o">;</span> <span class="n">array</span><span class="o">[</span><span class="mi">4</span><span class="o">]</span> <span class="o">=</span> <span class="mi">4</span><span class="o">;</span> <span class="k">for</span> <span class="o">(</span><span class="kt">int</span> <span class="nl">item:</span> <span class="n">array</span><span class="o">)</span> <span class="o">{</span> <span class="n">System</span><span class="o">.</span><span class="na">out</span><span class="o">.</span><span class="na">println</span><span class="o">(</span><span class="s">&quot;Foreach: &quot;</span> <span class="o">+</span> <span class="n">item</span><span class="o">);</span> <span class="o">}</span></code></pre></div> <h3>JavaScript</h3> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="kd">var</span> <span class="nx">array</span> <span class="o">=</span> <span class="k">new</span> <span class="nb">Array</span><span class="p">(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="mi">4</span><span class="p">);</span> <span class="k">for</span> <span class="p">(</span><span class="kd">var</span> <span class="nx">value</span> <span class="k">in</span> <span class="nx">array</span><span class="p">)</span> <span class="p">{</span> <span class="nb">document</span><span class="p">.</span><span class="nx">write</span><span class="p">(</span><span class="s1">&#39;Foreach: &#39;</span> <span class="o">+</span> <span class="nx">value</span> <span class="o">+</span> <span class="s1">&#39;&lt;br/&gt;&#39;</span> <span class="p">);</span> <span class="p">}</span></code></pre></div> <h3>PHP</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#950">$array</span> = <span style="color:#369;font-weight:bold">array</span>(<span style="color:#00D">0</span>, <span style="color:#00D">1</span>, <span style="color:#00D">2</span>, <span style="color:#00D">3</span>, <span style="color:#00D">4</span>); <span style="color:#080;font-weight:bold">foreach</span> (<span style="color:#950">$array</span> <span style="color:#080;font-weight:bold">as</span> <span style="color:#950">$key</span>=&gt;<span style="color:#950">$value</span>) { <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Foreach: </span><span style="color:#950">$value</span><span style="color:#D20">&lt;br/&gt;</span><span style="color:#710">&quot;</span></span>; } </pre></div> </div> </div> <h3>Python</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>array = [<span style="color:#00D">0</span>, <span style="color:#00D">1</span>, <span style="color:#00D">2</span>, <span style="color:#00D">3</span>, <span style="color:#00D">4</span>] <span style="color:#080;font-weight:bold">for</span> value <span style="color:#080;font-weight:bold">in</span> array: <span style="color:#080;font-weight:bold">print</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Foreach: %i</span><span style="color:#710">&quot;</span></span> % value </pre></div> </div> </div> <h2>More information</h2> <p>If you want to see the code, you can download this <a href="../images/2011/12/for-loops.zip">zip archive</a>.</p> <p>It is quite astonishing, but Wikipedia has a very long <a href="http://en.wikipedia.org/wiki/For_loop">article about for loops</a>.</p> Checkstyle //martin-thoma.com/checkstyle/ Wed, 30 Nov 2011 21:59:40 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/checkstyle <pre><code>&lt;li&gt;&lt;/li&gt; I have to go to a programming course at KIT at the moment where we are taught how to program with Java. They create exercises which get evaluated automatically. One part of the evaluation is checkstyle. </code></pre> <p>So it is a good idea to test the files on my machine before uploading them.</p> <h2>Installation</h2> <p>You can install it on an Ubuntu system with this command:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install checkstyle</code></pre></div> <h2>Usage</h2> <p>You can call checkstyle with this command:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">checkstyle -c /usr/share/checkstyle/sun_checks.xml YourCode.java</code></pre></div> <p>Another example would be:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">checkstyle -c /path/to/config/Progr_WS11_Checkstyle1.xml KITBook.java</code></pre></div> <p>It will generate some output similar to this:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Starting audit... KITBook.java:173:64: <span class="s1">&#39;{&#39;</span> is not preceded with whitespace. KITBook.java:174:69: <span class="s1">&#39;-&#39;</span> is not preceded with whitespace. KITBook.java:174:70: <span class="s1">&#39;-&#39;</span> is not followed by whitespace. Audit <span class="k">done</span>.</code></pre></div> <h2>Resolve warnings</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="o">[</span>warning<span class="o">]</span> /usr/bin/checkstyle: No java runtime was found <span class="o">[</span>warning<span class="o">]</span> /usr/bin/checkstyle: No JAVA_CMD <span class="nb">set </span><span class="k">for</span> run_java, falling back to <span class="nv">JAVA_CMD</span> <span class="o">=</span> java</code></pre></div> <p>You have to set the path:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nv">JAVA_CMD</span><span class="o">=</span>/usr/lib/jvm/java-6-sun/bin/java <span class="nb">export </span>JAVA_CMD</code></pre></div> <h2>Check all files in a folder</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">checkstyle -c /home/moose/Downloads/Progr_WS11_Checkstyle1.xml -r .</code></pre></div> <h2>Checkstyle and eclipse</h2> <p>Go to <code><u>H</u>elp &rarr; Install New <u>S</u>oftware ...</code></p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/eclipse-path-updates-300x173.png"><img src="../images/2011/11/eclipse-path-updates-300x173.png" alt="Install new software or plugins in eclipse" width="" height="" class="size-medium wp-image-9671" /></a><p class="wp-caption-text">Install new software or plugins in eclipse</p></div> <p>Install <code>http://eclipse-cs.sf.net/update/</code> as a new “repository”.</p> <p>After you have installed the plugin, you have to activate it for your project. To do so, you have to go to <code><u>P</u>roject &rarr; <u>P</u>roperties</code> and check <code>Checkstyle active for this project</code>. Then you have to change to the <code>Local Check Configurations</code> tab and load your personal checkstyle xml files.</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/eclipse-checkstyle-properties-300x104.png"><img src="../images/2011/11/eclipse-checkstyle-properties-300x104.png" alt="Checkstyle properties in eclipse" width="" height="" class="size-medium wp-image-9681" /></a><p class="wp-caption-text">Checkstyle properties in eclipse</p></div> <p>Click on <code>New</code>, give it a name and click on <code>import</code>. Go back to the main tab and use your personal checkstyle. You will have to rebuild the project.</p> <p>You might want to use more than one checkstyle file. You can do that if you uncheck <code>Use simple configuration</code>:</p> <div style="width: 608px" class="wp-caption aligncenter"><a href="../images/2011/11/eclipse-checkstyle-multiple-files.png"><img src="../images/2011/11/eclipse-checkstyle-multiple-files.png" alt="Multiple Checkstyle files in Eclipse" width="" height="" class="size-full wp-image-9711" /></a><p class="wp-caption-text">Multiple Checkstyle files in Eclipse</p></div> <p>Now you can set <code>File Set Configuration</code> to <code>All</code>, select your <code>Check Configuration</code>, click on <code>OK</code> and enable it in the <code>Main</code> tab.</p> <h2>Further reading and resources </h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Checkstyle">Wikipedia</a></li> <li><a href="http://checkstyle.sourceforge.net/index.html">Official Website</a></li> </ul> <h3>KIT</h3> <p>If you are a student at KIT and you can download the KIT checkstyle-files from <a href="http://zvi.ipd.kit.edu/lehre_programmieren_ws11.php#Zusaetzliches_Material">zvi.ipd.kit.edu</a>. If you can’t do it from home via VPN, you could use SSH.</p> <p>These commands work fine on Ubuntu and I guess on every Linux machine. If you use Windows, you will have to install Putty or something similar.</p> <p>Login with your personal account that begins with u. I’ll use uabcd in this example.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">ssh uabcd@rzstud.stud.uni-karlsruhe.de</code></pre></div> <p>Then download the files with wget:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">wget ftp://ftp.ira.uka.de/pub/ZVI/KIT/programmieren_ws11/material/Progr_WS11_Checkstyle1.xml wget ftp://ftp.ira.uka.de/pub/ZVI/KIT/programmieren_ws11/material/Progr_WS11_Checkstyle2.xml</code></pre></div> <p>Now you can exit the bash with <code>exit</code> and download the files from your account with <code>scp</code>:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">scp uabcd@rzstud.stud.uni-karlsruhe.de:~/Progr_WS11_Checkstyle1.xml ~/Progr_WS11_Checkstyle1.xml scp uabcd@rzstud.stud.uni-karlsruhe.de:~/Progr_WS11_Checkstyle1.xml ~/Progr_WS11_Checkstyle1.xml</code></pre></div> How to create a color scheme //martin-thoma.com/how-to-create-a-color-scheme/ Fri, 11 Nov 2011 08:22:09 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-create-a-color-scheme <p>Here are some nice online tools to create color schemes</p> <h2>Color Rotate</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/color-rotate-300x263.png"><img src="../images/2011/11/color-rotate-300x263.png" alt="Color Rotate" width="" height="" class="size-medium wp-image-9011" /></a><p class="wp-caption-text"><a href="http://www.colorotate.org/">Color Rotate</a></p></div> <h2>Color Scheme Designer</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/color-scheme-designer-300x198.png"><img src="../images/2011/11/color-scheme-designer-300x198.png" alt="Color Scheme Designer" width="" height="" class="size-medium wp-image-8991" /></a><p class="wp-caption-text"><a href="http://colorschemedesigner.com/">Color Scheme Designer</a></p></div> <h2>Color Jack</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/color-jack-sphere-300x174.png"><img src="../images/2011/11/color-jack-sphere-300x174.png" alt="Color Jack" width="" height="" class="size-medium wp-image-9021" /></a><p class="wp-caption-text"><a href="http://mudcu.be/sphere/">Color Jack</a></p></div> <h2>Pictaculous</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/Pictaculous1-300x240.png"><img src="../images/2011/11/Pictaculous1-300x240.png" alt="Pictaculous - A color Palette Generator" width="" height="" class="size-medium wp-image-8711" /></a><p class="wp-caption-text"><a href="http://pictaculous.com/">Pictaculous</a> - A color Palette Generator</p></div> <h2>4096 Color Wheel</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/4096-color-wheel-300x242.png"><img src="../images/2011/11/4096-color-wheel-300x242.png" alt="4096 Color Wheel" width="" height="" class="size-medium wp-image-8951" /></a><p class="wp-caption-text"><a href="http://www.ficml.org/jemimap/style/color/wheel.html">4096 Color Wheel</a></p></div> <h2>Kuler</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/kuler-300x210.png"><img src="../images/2011/11/kuler-300x210.png" alt="kuler" width="" height="" class="size-medium wp-image-8961" /></a><p class="wp-caption-text"><a href="http://kuler.adobe.com/">kuler</a></p></div> <h2>Colour Lovers</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/colour-lovers-300x223.png"><img src="../images/2011/11/colour-lovers-300x223.png" alt="COLOURlovers" width="" height="" class="size-medium wp-image-8981" /></a><p class="wp-caption-text"><a href="http://www.colourlovers.com/">COLOURlovers</a></p></div> <h2>Color Blender</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/11/color-blender-300x240.png"><img src="../images/2011/11/color-blender-300x240.png" alt="Color Blender" width="" height="" class="size-medium wp-image-9031" /></a><p class="wp-caption-text"><a href="http://www.colorblender.com/">Color Blender</a></p></div> Eine Sprache ist nicht regulär - Beweis mit dem Pumping-Lemma //martin-thoma.com/pumping-lemma/ Thu, 10 Nov 2011 16:05:33 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/pumping-lemma <p>Reguläre Sprachen können von endlichen Automaten erkannt werden. Das bedeutet, dass eine endliche Anzahl an Zuständen ausreicht, um ein Wort der Sprache zu akzeptieren. Wenn also eine Sprache <code>$L = \{a^i b^{2i} | i \in \mathbb{N}\}$</code> beschrieben wird, müsste gezählt werden, wie oft a vorkommt. a kann aber beliebig oft vorkommen. Das ist ein Indiz dafür, dass es sich nicht um eine reguläre Sprache handelt.</p> <p>Das <a href="http://de.wikipedia.org/wiki/Pumping-Lemma">Pumping-Lemma</a> ist ein notwendiges, aber kein hinreichendes Kriterium für reguläre Sprachen. Daraus folgt, dass eine nicht-reguläre Sprache eventuell durch das Lemma entlarvt werden kann. Allerdings muss nicht jede Sprache, die das Pumping-Lemma erfüllt, regulär sein.</p> <p>Dies kann man durch einen Widerspruchsbeweis zeigen. Dabei nimmt man an, dass die Behauptung falsch ist. Dann zeigt man, dass man durch die Annahme zu einem Widerspruch kommt.</p> <h2>Beispiel</h2> <p><strong>Voraussetzung</strong>:</p> <p><code>$L_2 = \{a^i b^j c^k | i \lt j \lt k\}$</code>.</p> <p><strong>Behauptung</strong>: <code>$L_2$</code> ist nicht regulär.</p> <p><strong>Beweis</strong>: (durch Widerspruch)</p> <p><strong>Annahme</strong>: <code>$L_2$</code> sei regulär.</p> <p>Aus dem Pumping-Lemma folgt: <code>$\exists n \in \mathbb{N}: \forall w \in \{w \in L_2 | |w| \geq n\}: $</code> <code>$\exists \text{ Darstellung } uvx = w \text{ mit } v \neq \varepsilon \land |uv| \leq n$</code> für die gilt:</p> <p><code>$uv^i x \in L_2 \forall i \in \mathbb{N}_0$</code></p> <p>In Worten: Wenn man ein Wort in L hat, dass mindestens so lang ist wie ein bestimmtes n, dann kann man dieses Wort in Teilworte u, v und x zerlegen. Bei dieser Zerlegung ist v niemals leer. Wenn man nun den Teil des Wortes, der in v steckt wiederholt, muss das Wort immer noch in <code>$L_2$</code> sein.</p> <p>Sei <code>$n \in \mathbb{N}$</code> die Konstante aus dem Pumping-Lemma.</p> <p>Betrachte nun <code>$w = a^n b^{n+1} c^{n+2}$</code>. Offensichtlich gilt <code>$w \in L_2$</code>. Da <code>$|uv| \leq n$</code> muss in v mindestens ein a sein.</p> <p><code>$\Rightarrow uv^2 x = a^{n+2 \cdot i} b^{n+1} c^{n+2}, i \geq 1 $</code> <code>$\Rightarrow uv^2x \notin L_2 $</code> <code>$\Rightarrow \text{Widerspruch} $</code> <code>$\Rightarrow \text{Die Annahme war falsch.} $</code> <code>$\Rightarrow L_2$</code> ist nicht regulär.</p> <p><em>Bemerkung</em>: Eigentlich ist es ein Beweis durch Kontraposition. Man weiß, es gilt: <code>$L \in {\cal L_3} \Rightarrow $</code> L erfüllt das Pumping-Lemma. Daraus folgt: L erfüllt nicht das Pumping-Lemma <code>$\Rightarrow L \notin {\cal L_3}$</code>. Um zu beweisen, dass L das Pumping-Lemma nicht erfüllt, benutzt man meist einen Widerspruchsbeweis wie oben.</p> <h2>Material</h2> <p>Ich habe mal ein paar <a href="../images/2011/11/odgen-pumping.zip">Beispiele für Ogdens Lemma und das Pumping-Lemma</a> gesammelt.</p> Python Generators //martin-thoma.com/python-generators/ Thu, 10 Nov 2011 08:24:00 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-generators <p>Python has a quite mighty tool: Generators.</p> <p>Generators help you to program interators. They look almost like normal functions, but they have yield as a special keyword. yield is used instead of return.</p> <p>Imagine you wanted to display n fibonacci numbers. This could be your normal approach:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">fibonacci</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Build and return a list of the first </span> <span class="sd"> n &gt;= 2 Fibonacci numbers &quot;&quot;&quot;</span> <span class="n">fibList</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">]</span> <span class="k">while</span> <span class="nb">len</span><span class="p">(</span><span class="n">fibList</span><span class="p">)</span> <span class="o">&lt;</span> <span class="n">n</span><span class="p">:</span> <span class="n">newFib</span> <span class="o">=</span> <span class="n">fibList</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="n">fibList</span><span class="p">[</span><span class="o">-</span><span class="mi">2</span><span class="p">]</span> <span class="n">fibList</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">newFib</span><span class="p">)</span> <span class="k">return</span> <span class="n">fibList</span> <span class="k">for</span> <span class="n">nr</span><span class="p">,</span> <span class="n">fib</span> <span class="ow">in</span> <span class="nb">enumerate</span><span class="p">(</span><span class="n">fibonacci</span><span class="p">(</span><span class="mi">100</span><span class="p">)):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;The </span><span class="si">%i</span><span class="s">-th Fibonacci-Nr is </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">nr</span><span class="p">,</span> <span class="n">fib</span><span class="p">))</span></code></pre></div> <p>The disadvantage of this approach is that you have to keep every element of the sequence in memory. Of course, you could write something like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">fib</span><span class="p">(</span><span class="n">n</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot; Calculate the n-th fibonacci number. &quot;&quot;&quot;</span> <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span> <span class="k">return</span> <span class="mi">0</span> <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span> <span class="k">return</span> <span class="mi">1</span> <span class="k">else</span><span class="p">:</span> <span class="k">return</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">fib</span><span class="p">(</span><span class="n">n</span><span class="o">-</span><span class="mi">2</span><span class="p">)</span> <span class="k">for</span> <span class="n">nr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="mi">100</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;The </span><span class="si">%i</span><span class="s">-th Fibonacci-Nr is </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">nr</span><span class="p">,</span> <span class="n">fib</span><span class="p">(</span><span class="n">nr</span><span class="p">)))</span></code></pre></div> <p>This needs much less memory, but much more time. You have to recalculate the first few fibonacci numbers every time.</p> <p>A generator could look like this:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="k">def</span> <span class="nf">fibGenerator</span><span class="p">():</span> <span class="sd">&quot;&quot;&quot; A python fibonacci generator &quot;&quot;&quot;</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span> <span class="k">while</span> <span class="mi">1</span><span class="p">:</span> <span class="k">yield</span> <span class="n">a</span> <span class="n">a</span><span class="p">,</span> <span class="n">b</span> <span class="o">=</span> <span class="n">b</span><span class="p">,</span> <span class="n">a</span> <span class="o">+</span> <span class="n">b</span> <span class="n">myGenerator</span> <span class="o">=</span> <span class="n">fibGenerator</span><span class="p">()</span> <span class="k">for</span> <span class="n">nr</span> <span class="ow">in</span> <span class="nb">xrange</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="mi">100</span><span class="p">):</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;The </span><span class="si">%i</span><span class="s">-th Fibonacci-Nr is </span><span class="si">%i</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">nr</span><span class="p">,</span> <span class="n">myGenerator</span><span class="o">.</span><span class="n">next</span><span class="p">()))</span></code></pre></div> <h2>Further Reading</h2> <ul> <li><a href="http://docs.python.org/tutorial/classes.html#generators">Python documentation</a></li> <li><a href="http://wiki.python.org/moin/Generators">Python Wiki</a></li> </ul> Wie führe ich einen Induktionsbeweis? //martin-thoma.com/wie-fuhre-ich-einen-induktionsbeweis/ Tue, 01 Nov 2011 01:29:35 +0100 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-fuhre-ich-einen-induktionsbeweis <p>Der Induktionsbeweis eignet sich häufig, wenn es um Aussagen über die Natürlichen Zahlen <code>$\mathbb{N}$</code> geht, allerdings kann er auch für die ganzen Zahlen <code>$\mathbb{Z}$</code> verwendet werden.</p> <h2>Prinzip</h2> <p>Der Gedanke hinter dem Induktionsbeweis ist, dass man sehr leicht für ein einzelnes Element zeigen kann, dass eine Aussage gilt. Diese Aussage ist die Behauptung. Dann zeigt man allgemein, wenn die Aussage für eine Zahl gilt muss sie auch für die nächste Zahl gelten.</p> <p>Wenn man also für n = 1 zeigt dass die Aussage A(n) korrekt ist, dann gilt sie für alle positiven Zahlen.</p> <h2>Aufbau</h2> <ul> <li><strong>Induktionsanfang</strong> (I.A.): Zeige, dass die Aussage f&uuml;r ein bestimmtes `$n_0$` (also z.B. `$n_0 = 0$`) gilt. Daf&uuml;r muss man einfach nur einsetzen.</li> <li><strong>Induktionsvorraussetzung</strong> (I.V.)): "Sei `$n \in \mathbb{N}$` beliebig, aber fest und es gelte: <aussage>" <li><strong>Induktionsschluss</strong> (I.S.): Ausgehend von I.V. ist zu zeigen, dass die Aussage f&uuml;r `$n_0 + 1$` gilt.</li> <h2>Beispiele</h2> <h3>Identit&auml;ten</h3> Es gibt viele Identit&auml;ten, die sich gut mit einem Induktionsbeweis zeigen lassen: Bei den folgenden Identit&auml;ten sei `$n \in \mathbb{N}$`. <h4>Gau&szlig;sche Summenformel</h4> <strong>Behauptung</strong>: `$\sum_{k=1}^n k = \frac{1}{2} \cdot n \cdot (n+1)$` <strong>Beweis</strong>: durch vollst&auml;ndige Induktion <strong>I.A.</strong>: Sei n = 1. Dann: `$\sum_{k=1}^1 k = 1 = \frac{1}{2} \cdot 1 \cdot (1+1)$` <strong>I.V.</strong>: Sei `$n \in \mathbb{N}$` beliebig, aber fest und es gelte: `$\sum_{k=1}^n k = \frac{1}{2} \cdot n \cdot (n+1)$` <strong>I.S.</strong>: `$\sum_{k=1}^{n+1} k = \sum_{k=1}^{n} k + (n+1) \stackrel{I.V.}{=} \frac{1}{2} \cdot n \cdot (n+1) + (n+1) = $` `$= \frac{1}{2} \cdot (n^2 + n) + (n+1) = \frac{1}{2} \cdot (n^2 + 3n + 2) = \frac{1}{2} \cdot (n+1)(n+2) \blacksquare$` <h4>Weitere</h4> <ol type="i" style="list-style-type:lower-roman"> <li>`$\sum_{k=1}^n k^3 = \frac{1}{4}n^2 (n+1)^2$`</li> <li>Fibonacci: `$f(m+n) = f(n+1) \cdot f(m) + f(n) \cdot f(m-1)$`</li> </ol> <h3>Binomischer Satz</h3> Das folgende habe ich als Mitschrift der Vorlesung "Analysis I" am KIT gemacht: <div style="background-color:#FFFF66;border:2px solid #FF0000;padding:5px;"> Seien `$a, b \in \mathbb{R}.$` Dann gilt f&uuml;r alle `$n \in \mathbb{N}$`: `$(a+b)^{n+1} = (a+b)(a+b)^n = (a+b) \underbrace{\sum_{k=0}^{n} \binom{n}{k} a^{n-k} b^k}_\text{Binomischer Lehrsatz}$` </div> <strong>I.A.</strong>: `$n=1: \sum_{k=0}^{1}\binom{1}{k} a^{1-k} b^k = (a+b)^n$` <strong>I.V.</strong>: Sei `$n \in \mathbb{N}$` und es gelte `$(a+b)^{n+1} = (a+b)(a+b)^n = (a+b) \sum_{k=0}^{n} \binom{n}{k} a^{n-k} b^k$` <strong>I.S.</strong>: `$ \begin{align} (a+b)^{k+1} &amp;= (a+b)(a+b)^n \\ &amp;= (a+b) \sum_{k=0}^{n} \binom{n}{k} a^{n-k} b^k \\ &amp;= \sum_{k=0}^{n} \binom{n}{k} a^{n+1-k} b^k + \sum_{k=0}^n \binom{n}{k} a^{n-k} b^{k+1} \\ &amp;= \underbrace{\binom{n}{0}}_{\binom{n+1}{0}} a^{n+1} + \sum_{k=1}^n \binom{n}{k} a^{n+1-k} b^k + \underbrace{\sum_{k=0}^{n-1} \binom{n}{k} a^{n-k} b^{k+1}}_\text{Vorbemerkung} + \binom{n}{n} b^{n+1} \\ &amp;= \binom{n+1}{0} a^{n+1} + \sum_{k=1}^{n} [\binom{n}{k} + \binom{n}{k-1}] a^{n+1} b^k + \binom{n+1}{n+1} b^{n+1} \\ &amp;= \sum_{k=0}^{n+1} \binom{n+1}{k} a^{n+1-k} b^k \end{align}$` <h3>Rekursive Folgen</h3> Der Grenzwert rekursiv definierter Folgen l&auml;sst sich h&auml;ufig sehr sch&ouml;n mit mehreren Induktionsbeweisen beweisen. <ol> <li>Finde f&uuml;r dich heraus: Ist die Folge monoton steigend oder fallend? ist 0 oder 1 eine untere / obere Schranke? gibt es andere untere oder obere Schranken?</li> <li>Beweise, dass du eine obere / untere Schranke gefunden hast</li> <li>Beweise, dass die Folge monoton steigt / f&auml;llt</li> <li>Mache den Ansatz: Sei `$a$` der Grenzwert der Folge `$(a_n)_{n \in \mathbb{N}}$` mit `$a_n = f(a_{n-1})$`. Dann gilt: `$a = f(a)$`. L&ouml;se dann nach `$a$` auf.</li> </ol> Eine Folge in der das wunderbar klappt ist folgende: Sei `$(a_n)_{n \in \mathbb{N}}$` eine Folge und definiert durch: `$a_0 = 2,~~~~~ a_n = \sqrt[3]{a_n^2+a_n-1}$`. <h2>Strukturelle Induktion</h2> Bei der vollst&auml;ndigen Induktion iteriert man &uuml;ber eine nat&uuml;rliche Zahl und gelangt so, ab einer festen nat&uuml;rlichen Zahl `$n_0$` zu jeder beliebigen gr&ouml;&szlig;eren nat&uuml;rlichen Zahl. Die strukturelle Induktion nutzt allerdings nicht direkt Zahlen, sondern strukturen. Man hat eine sog. "Atomare Struktur" bzw. "Atomares Element", also in einem gewissen Sinn das oder die kleinsten Teilchen, gegeben. Diese Teilchen erf&uuml;llen die Aussage. Nun zeigt man, dass aus den Atomaren Elementen alle Strukturen gebildet werden k&ouml;nnen, &uuml;ber die in der Behauptung die Aussage getroffen wird und dass die Aussage bei jeder neuen Struktur richtig ist. Insbesondere bietet sich die strukturelle Induktion bei komplexen Graphen, aussagelogischen Formeln und W&ouml;rtern an. <h3>Beispiele</h3> <h4>Voller, vollst&auml;ndiger Bin&auml;rbaum</h4> Sei G(V, E) ein Bin&auml;rbaum. G ist ein voller Bin&auml;rbaum `$: \Leftrightarrow$` alle inneren Knoten von G haben den Verzweigungsgrad 2 G ist ein voller, vollst&auml;ndiger Bin&auml;rbaum `$: \Leftrightarrow$` G ist ein voller Bin&auml;rbaum und alle Bl&auml;tter haben die gleiche H&ouml;he <strong>Behauptung</strong> `${\cal B} (n)$`: Jeder volle, vollst&auml;ndige Bin&auml;rbaum der H&ouml;he `$n, n \in \mathbb{N}$` hat `$2^{n-1} - 1$` innere Knoten. <strong>Beweis</strong>: durch strukturelle Induktion <strong>I.A.</strong>: zeige `${\cal B} (1)$`. Ein voller, vollst&auml;ndiger Bin&auml;rbaum der H&ouml;he n = 1 besteht nur aus einem Knoten. Er hat also `$0 = 2^{n-1} - 1 = 2^{1-1} - 1 = 2^0 - 1 = 1 - 1 = 0$` innere Knoten. <strong>I.V.</strong>: F&uuml;r beliebige, aber feste volle, vollst&auml;ndige Bin&auml;rb&auml;ume G der H&ouml;he n gilt: G hat `$2^{n-1} - 1$` innere Knoten. <strong>I.S.</strong>: zeige `${\cal B} (n+1)$` F&uuml;r jeden vollen, vollst&auml;ndigen Bin&auml;rbaum der H&ouml;he `$n+1$` gibt es einen Teilgraphen T, der ein voller, vollst&auml;ndiger Bin&auml;rbaum der H&ouml;he n ist. `$\stackrel{I.V.}{\Rightarrow}$` T hat `$2^{n-1} - 1$` innere Knoten. Das sind auch innere Knoten von G. Da die H&ouml;he von G um eins h&ouml;her ist als die von T und sowohl G als auch T volle, vollst&auml;dige Bin&auml;rbaume sind, kommen zu jedem der `$2^{n-1}$` Bl&auml;tter aus T noch 2 Bl&auml;tter. Dadurch hat G genau `$2^{n-1}$` innere Knoten mehr als T `$\Rightarrow$` G hat `$2^{n-1}-1+2^{n-1} = 2^n - 1$` innere Knoten `$\blacksquare$` <h4>Aussagenlogische Ausdr&uuml;cke</h4> Die Idee habe ich aus dem <a href="http://www.matheboard.de/archive/470377/thread.html">Matheboard</a> von "MoeMoeson". Bei diesem Beweis bin ich mir aber nicht sicher, ob es tats&auml;chlich strukturelle Induktion ist :-/ Definition: Aussagenlogischer Ausdruck <ol type="i" style="list-style-type: lower-roman;"> <li>Jede Variable `$p_i, i \in \mathbb{N}$` ist ein aussagenlogischer Ausdruck &uuml;ber V.</li> <li>Sind A und B aussagenlogische Ausdr&uuml;cke &uuml;ber V, so sind auch `$\neg A, A \land B, A \lor B, A \Rightarrow B, A \Leftrightarrow B, (A)$`.</li> <li>Ein Wort &uuml;ber V ist nur dann ein aussagenlogischer Ausdruck &uuml;ber V, falls dies aufgrund endlich oftmaliger Anwendung von (i) und (ii) der Fall ist.</li> </ol> <strong>Behauptung</strong> Jeder aussagenlogischer Ausdruck endet entweder auf eine Variable oder auf eine schlie&szlig;ende Klammer. <strong>Beweis</strong>: durch strukturelle Induktion <strong>I.A.</strong>: Jeder aussagenlogischer Ausdruck aus (i) endet auf eine Variable. <strong>I.V.</strong>: F&uuml;r beliebige, aber feste aussagenlogische Ausdr&uuml;cke A gilt: A endet auf eine Variable oder eine schlie&szlig;ende Klammer. <strong>I.S.</strong>: Ein aussagenlogischer Ausdruck kann nur durch endlich h&auml;ufige Anwendung von (i) und (ii) erzeugt werden (vgl. (iii)). (i) erf&uuml;llt die Bedingung laut I.V., (ii) auch. `$\blacksquare$` <strong>Behauptung</strong> F&uuml;r jeden aussagenlogischen Ausdruck A gibt es einen &auml;quivalenten aussagenlogischen Ausdruck B, der nur `$\neg$` und `$\land$` als Operatoren verwendet. <strong>Beweis</strong>: durch strukturelle Induktion <strong>I.A.</strong>: Seien `$p_1, p_2$` aussagenlogische Variablen. Dann gilt: `$p_1 \lor p_2 = \neg (\neg p_1 \land \neg p_2)$` `$p_1 \Leftrightarrow p_2 = \neg (p_1 \land \neg p_2) \land \neg (\neg p_1 \land p_2)$` `$p_1 \Rightarrow p_2 = p_1 \land \neg p_2$` F&uuml;r alle weiteren Ausdr&uuml;cke aus (i) und (ii) gilt die Behauptung offensichtlich. <strong>I.V.</strong>: F&uuml;r beliebige, aber feste aussagenlogische Ausdr&uuml;cke A gilt: Es gibt einen &auml;quivalenten aussagenlogischen Ausdruck B, der nur `$\neg$` und `$\land$` als Operatoren verwendet. <strong>I.S.</strong>: Ein aussagenlogischer Ausdruck kann nur durch endlich h&auml;ufige Anwendung von (i) und (ii) erzeugt werden (vgl. (iii)). (i) und (ii) erf&uuml;llen die Bedingung laut I.V.. `$\blacksquare$` <h2>Unendlich - Wann Induktion nicht funktioniert</h2> Mit Induktion kann man Aussagen f&uuml;r beliebig gro&szlig;e/kleine ganze Zahlen treffen. Allerdings eben nur f&uuml;r ganze Zahlen. Unendlich ist keine ganze Zahl. Also kann man auch keine Aussagen f&uuml;r "unendliche Aussagen" treffen. Hier ein Beispiel: Sei A eine Menge. A hei&szlig;t offen `$:\Leftrightarrow \forall_{x \in A} : \exists_{\delta = \delta(x) &gt; 0} : U_\delta(x) \subseteq A$` Es gilt: U und V sind offene Mengen `$\Rightarrow U \cap V$` ist offen.* Nun k&ouml;nnte man den Trugschluss machen, dass der Schnitt unendlich vieler offener Mengen auch offen ist. Der <strong>falsche Induktionsbeweis</strong> w&uuml;rde in etwa so aussehen: <strong>Voraussetungen:</strong> Seien `$M_i, i \in \mathbb{N}_0$` offene Mengen. Sei M eine Menge und definiert durch `$M := \displaystyle \bigcap_{i=0}^\infty M_i$`. <strong>Behauptung</strong>: M ist offen. <strong>Beweis</strong>: durch vollst&auml;ndige Induktion <strong>I.A.</strong>: Sei n = 1. Dann: `$\cap_{i=0}^1 M_i = M_0 \cap M_1$` ist laut * offen. <strong>I.V.</strong>: Sei `$n \in \mathbb{N}$` beliebig, aber fest und es gelte: `$\displaystyle \bigcap_{i=0}^n M_i$` ist offen. <strong>I.S.</strong>: `$\displaystyle \bigcap_{i=0}^{n+1} M_i = \bigcap_{i=0}^{n} M_i \cap M_{n+1}$`. Nun gilt: `$\displaystyle \bigcap_{i=0}^{n} M_i$` ist per I.V. offen. `$M_{n+1}$` ist per Vorraussetzung offen. Der Schnitt von beiden ist wegen * offen. Da n beliebig gro&szlig; werden kann, ist auch M offen `$\blacksquare$` Allerdings gilt: `$\displaystyle \bigcap_{n=1}^\infty \left (1 - \frac{1}{n}, 2+\frac{1}{n} \right) = [1, 2]$`, also ein Gegenbeispiel. Der "Beweis" ist also offensichtlich falsch. Wo ist aber der Fehler? Man hat gezeigt, dass beliebig viele Schnitte von offenen Mengen wieder offen sind. Die Behauptung sagt aber, dass unendlich viele Schnitte offener Mengen wieder offen sind. Es gibt also einen unterschied zwischen "beliebig viel" und "unendlich". <h2>Weitere &Uuml;bungen</h2> <ul> <li>KIT, GBI: <a href="http://gbi.ira.uka.de/archiv/2008/blatt-uebung2-aufgaben.pdf">Zusatzblatt 2</a>, &Uuml;bungsaufgabe 16 - <a href="http://gbi.ira.uka.de/archiv/2008/blatt-uebung2-aufgaben.pdf">L&ouml;sungen</a></li> <li>KIT, GBI: <a href="http://gbi.ira.uka.de/archiv/2008/blatt-uebung3-aufgaben.pdf">Zusatzblatt 3</a>, &Uuml;bungsaufgabe 26 d) und 38 d) - <a href="http://gbi.ira.uka.de/archiv/2008/blatt-uebung3-loesungen.pdf">L&ouml;sungen</a></li> <li>Otto Forster: &Uuml;bungsbuch zur Analysis I, 5. Auflage, S. 3 - 6. ISBN 978-3-8348-1252-0.</li> </ul> <h2>Quellen</h2> <ul> <li>Otto Forster: Analysis I, 10. Auflage, S. 1 - 11. ISBN 978-3-8348-1251-3. (Sehr zu empfehlen!)</li> <li><a href="http://gbi.ira.uka.de/uebungen/uebung-2.pdf">Folien zur GBI-&Uuml;bung</a> am KIT</li> <li><a href="http://gbi.ira.uka.de/vorlesungen/VL11.01.2012.pdf">Vorlesung vom 11.01.2012</a></li> <li><a href="http://mitschriebwiki.nomeata.de/WS07/Ana1.html">Analysis I Skript</a> (inoffiziell)</li> </ul> </aussage></li></ul> Prädikatenlogik: Aussagen formalisieren //martin-thoma.com/pradikatenlogik-aussagen-formalisieren/ Sat, 29 Oct 2011 15:12:33 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/pradikatenlogik-aussagen-formalisieren <p>Es ist häufig von Vorteil, wenn man Aussagen formalisieren kann. Es ist beispielsweise gar nicht so leicht das exakte Gegenteil einer Aussage zu finden.</p> <h2>Allgemeines zur Pr&auml;dikatenlogik</h2> <p>x sei im folgenden eine Aussage <code>$\neg x$</code>: Die Negation der Aussage x</p> <p><code>$\exists x$</code>: Es existiert mindestens ein x (Quantor) <code>$\forall x$</code>: Alle x (Quantor)</p> <p><code>$\land$</code>: und (eine Verknüfung zweier Aussagen) <code>$\lor$</code>: oder (eine Verknüfung zweier Aussagen). Im Deutschen wird oder meistens exklusiv, also im Sinne “entweder … oder …” verwendet. Dieses oder ist inklusiv, also “entweder … oder … oder beides”.</p> <p>Ich habe die Symbole bewusst in diesen Paragraphen angeordnet. Wird die Negation eines Ausdrucks gebildet, werden alle Symbole im Inneren durch das jeweils andere Symbol ersetzt. Beispielsweise wird das logische “und” zu einem “oder”.</p> <p>Ein kleiner Nachtrag: Was macht man, wenn man sagen will, dass eine Aussage A für genau ein Element x einer Menge M gilt? <code>$\exists x \in M: A(x) \land \forall (y \in M, y \neq x): \neg A(y)$</code></p> <h2>Karlsruher und die Verkehrsmittel</h2> <p>Folgendes Beispiel hatte ich in einem Tutorium am KIT:</p> <blockquote>(i) Alle Karlsruher fahren mit dem Rad oder der Stra&szlig;enbahn.</blockquote> <p>Was ist das Gegenteil dieser Aussage? Folgendes wäre denkbar:</p> <ol> <li>Kein Karlsruher f&auml;hrt mit dem Rad oder der Stra&szlig;enbahn.</li> <li>Kein Karlsruher f&auml;hrt mit dem Rad und der Stra&szlig;enbahn.</li> <li>Alle Karlsruher fahren mit dem Rad und der Stra&szlig;enbahn.</li> <li>Alle Karlsruher fahren nicht mit dem Rad und der Stra&szlig;enbahn.</li> <li>Es fahren nicht alle Karlsruher mit dem Rad oder der Stra&szlig;enbahn.</li> <li>Es fahren nicht alle Karlsruher mit dem Rad und der Stra&szlig;enbahn.</li> <li>...</li> </ol> <p>Nun wurde mir beigebracht, dass folgendes eine “saubere” Formalisierung der ersten Aussage ist:</p> <p>Sei K die Menge aller Karlsruher. Sei F Aussageform auf K und definiert durch <code>$F(k) := \text{"k f&amp;auml;hrt mit dem Fahrrad"} (k \in K)$</code> Sei analog S Aussageform auf K mit <code>$S(k) := \text{"k f&amp;auml;hrt mit der Stra&amp;szlig;enbahn"}$</code></p> <p>Dann lautet (i) formalisiert: <code>$\forall k \in K: F(k) \lor S(k)$</code> <small>(sprich: “Für alle k in K gilt: F von k oder S von k”)</small></p> <p>Negiert: <code>$\exists k \in K: \neg F(k) \land \neg S(k)$</code> <small>(sprich: “Es existiert mindestens ein k in K für das gilt: Es ist F von k nicht wahr und zugleich S von k nicht wahr.”)</small></p> <p>Übersetzt man das in einen schöneren deutschen Satz kann man sagen: Mindestens ein Karlsruher fährt weder mit dem Rad noch mit der Bahn.</p> <p>Wenn man das nun auf die oben angegebenen Lösungen bezieht, könnte es Aussage 5 oder 6 sein. Der Sinngemäß muss es heißen: Es fahren nicht alle Karlsruher entweder mit dem Rad, der Straßenbahn oder beidem. Ich tendiere stark dazu, Satz 5 zu nehmen. Allerdings bin ich mir nicht sicher, ob mein Sprachgefühl mich täuscht.</p> <h2>W&ouml;chentliches Fernsehprogramm</h2> <p>Noch ein Beispiel aus meinem Tutorium:</p> <blockquote>(ii) Im Fernsehen l&auml;uft jede Woche "Die Simpsons", "Die Ludolfs" und "Telekolleg".</blockquote> <p>Sei W die Menge aller Wochen. Sei A Aussageform auf W.</p> <p>A(w) := In der Woche w läuft “Die Simpsons”. <code>$w \in W$</code> B(w) := In der Woche w läuft “Die Ludolfs”. <code>$w \in W$</code> C(w) := In der Woche w läuft “Telekolleg”. <code>$w \in W$</code></p> <p>Dann lautet (ii) formalisiert: <code>$\forall w \in W: A(w) \land B(w) \land C(w)$</code></p> <p>Negiert: <code>$\exists w \in W: \neg A(w) \lor \neg B(w) \lor \neg C(w)$</code></p> <h2>Teilbarkeit</h2> <p>Nun mal etwas eigenes:</p> <blockquote>(iii) Jede gerade Zahl ist durch zwei teilbar.</blockquote> <p>Sei M die Menge der geraden Zahlen. Dann lautet (iii) formalisiert: <code>$\forall m \in M: x = \frac{m}{2} \implies x \in \mathbb{N}$</code></p> <h2>Weitere Materialien</h2> <ul> <li><a href="http://lrb.cs.uni-dortmund.de/~tick/Lehre/WS10/Logik/01-introw.pdf">Uni Dortmund</a>: 15 Seiten zum Formalisieren vom Aussagen</li> <li><a href="http://page.math.tu-berlin.de/~schmitt/lina0910/loesungen/loesung01.pdf">TU-Berlin</a> (Aufgabe 4 - " Jeder, der ein gutes Gehor hat, kann richtig singen[...]")</li> </ul> Konstruktion eines deterministischen endlichen Automaten aus einem nicht-deterministischem //martin-thoma.com/konstruktion-eines-deterministischen-endlichen-automaten-aus-einem-nicht-deterministischem/ Sat, 29 Oct 2011 10:21:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/konstruktion-eines-deterministischen-endlichen-automaten-aus-einem-nicht-deterministischem <p>Der nicht-deterministische endliche Automat zu dem regulärem Ausdruck <code>$(a \cup (ab(b)^\text{*}ba))^\text{*}$</code> ist folgender: <code>$Q = \{S, q_1, q_2\}$</code> <code>$\Sigma = \{a, b\}$</code> <code>$\delta = \text{siehe Grafik}$</code> <code>$F = \{S\}$</code> <code>$NEA = \left( Q, \Sigma, \delta, S, F \right)$</code></p> <div style="width: 375px" class="wp-caption aligncenter"><a href="../images/2011/10/myFiniteStateMachine1.png"><img src="../images/2011/10/myFiniteStateMachine1.png" alt="Nondeterministic finite-state machine" width="" height="" class="size-full wp-image-8141 " /></a><p class="wp-caption-text">Nondeterministic finite-state machine</p></div> <p>Will man daraus nun den endlichen Automaten konstruieren, läuft das im Prinzip über eine Potenzmengenkonstruktion.</p> <p>Zuerst defnieren wir: <code>$\tilde{S} = E(S) = \{S\}$</code></p> <p>Dann erstellen wir folgende Tabelle:</p> <table style="border:1px solid #000;"> <tr> <th style="border:1px solid #000;">`$\tilde{S}$`</th> <th style="border:1px solid #000;">{S}</th> </tr> <tr> <th style="border:1px solid #000;">a</th> <td style="border:1px solid #000;">&nbsp;</td> </tr> <tr> <th style="border:1px solid #000;">b</th> <td style="border:1px solid #000;">&nbsp;</td> </tr> </table> <p>Dann überprüft man, welche Zustände erreicht werden können, wenn man vom jedem Zustand in der Startmenge (hier also nur S) a einliest. Das ist in diesem Fall q1 oder S. Also haben wir eine weitere Zustandsmenge {q1, S}. Diese wird als neue Spalte in unsere Tabelle geschrieben:</p> <table style="border:1px solid #000;"> <tr> <th style="border:1px solid #000;">`$\tilde{S}$`</th> <th style="border:1px solid #000;">{S}</th> <th style="border:1px solid #000;">{q1, S}</th> </tr> <tr> <th style="border:1px solid #000;">a <td style="border:1px solid #000;">{q1, S}</td> <td style="border:1px solid #000;">&nbsp;</td> <tr> <th style="border:1px solid #000;">b</th> <td style="border:1px solid #000;">&nbsp;</td> <td style="border:1px solid #000;">&nbsp;</td> </tr> Nun geht man also jede Spalte, von links nach rechts durch. F&uuml;r jede Spalte wird jede Zeile, von oben nach unten, &uuml;berpr&uuml;ft. Mit jeder &Uuml;berpr&uuml;fung kann eine neue Zustandsmenge als Spalte hinzukommen. Die Anzahl der Zeilen ist eine Kopfzeile + die Anzahl der Zeichen im Eingabealphabet. Am Ende schaut die Tablle wie folgt aus: <table style="border:1px solid #000;"> <tr> <th style="border:1px solid #000;">`$\tilde{S}$`</th> <th style="border:1px solid #000;">{S}</th> <th style="border:1px solid #000;">{q1, S}</th> <th style="border:1px solid #000;">`$\emptyset$`</th> <th style="border:1px solid #000;">{q2}</th> <th style="border:1px solid #000;">{q1, q2}</th> </tr> <tr> <th style="border:1px solid #000;">a <td style="border:1px solid #000;">{q1, S}</td> <td style="border:1px solid #000;">{q1, S}</td> <td style="border:1px solid #000;">`$\emptyset$`</td> <td style="border:1px solid #000;">`$\emptyset$`</td> <td style="border:1px solid #000;">{S}</td> <tr> <th style="border:1px solid #000;">b</th> <td style="border:1px solid #000;">`$\emptyset$`</td> <td style="border:1px solid #000;">{q2}</td> <td style="border:1px solid #000;">`$\emptyset$`</td> <td style="border:1px solid #000;">{q1, q2}</td> <td style="border:1px solid #000;">{q1, q2}</td> </tr> `$\tilde{Q} = \{\{S\}, \{q_1, S\}, \{q_2\}, \{q_1, q_2\}\}$` `$\tilde{F} = \{\{S\}, \{q_1, S\}\}$` Die &Uuml;bergangsfunktion wurde mit dieser Tabelle schon hinreichend dargestellt. Nun folgt eine Darstellung der deterministischen Variante des nichtdeterministischen Automaten: <div style="width: 522px" class="wp-caption aligncenter"><a href="../images/2011/10/deterministic-fsm.png"><img src="//martin-thoma.com/captions/deterministic-fsm.png" alt="Deterministic Finite State machine (create from a non-deterministic version)" width="390" height="196" class="size-full wp-image-8421" /></a><p class="wp-caption-text">Deterministic Finite State machine (create from a non-deterministic version)</p></div> <h2>Material</h2> Die .gv sieht so aus: <div class="highlight"><pre><code class="language-text" data-lang="text">digraph finite_state_machine { rankdir=LR; size=&quot;8,5&quot; node [shape = doublecircle, label=&quot;{S}&quot;] S; node [shape = doublecircle, label=&quot;{q1, S}&quot;] q1S; node [shape = circle, label=&quot;{q2}&quot;] q2; node [shape = circle, label=&quot;{q1, q2}&quot;] q1q2; node [shape = circle, label=&quot;{}&quot;] T; node [shape = point ]; qi qi -&gt; S; S -&gt; q1S [ label = &quot;a&quot; ]; S -&gt; T [ label = &quot;b&quot; ]; q1S -&gt; q1S [ label = &quot;a&quot;]; q1S -&gt; q2 [ label = &quot;b&quot;]; q2 -&gt; T [ label = &quot;a&quot;]; q2 -&gt; q1q2 [ label = &quot;b&quot;]; q1q2 -&gt; S [ label = &quot;a&quot;]; q1q2 -&gt; q1q2 [ label = &quot;b&quot;]; T -&gt; T [label = &quot;a, b&quot;]; }</code></pre></div> Unter Linux kann man mit <a href="http://wiki.ubuntuusers.de/Graphviz">GraphViz</a> mit folgendem Befehl die Datei erstellen: <div class="highlight"><pre><code class="language-bash" data-lang="bash">dot -Tpng graph.gv -o deterministic-fsm.png</code></pre></div> </th></tr></table></th></tr></table> How to draw a finite-state machine //martin-thoma.com/how-to-draw-a-finite-state-machine/ Sat, 29 Oct 2011 09:37:50 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/how-to-draw-a-finite-state-machine <p><a href="http://en.wikipedia.org/wiki/Deterministic_finite-state_machine">Finite-state machines</a> are necessary to show that some problems are computable (or not).</p> <p>As I am currently learning something about them, I would like to be able to plot those finite automatons automatically. I will use <a href="http://www.graphviz.org/">graphviz</a>.</p> <h2>Nondeterministic finite-state machine</h2> <div style="width: 375px" class="wp-caption aligncenter"><a href="../images/2011/10/myFiniteStateMachine1.png"><img src="../images/2011/10/myFiniteStateMachine1.png" alt="Nondeterministic finite-state machine" width="" height="" class="size-full wp-image-8141 " /></a><p class="wp-caption-text">Nondeterministic finite-state machine</p></div> <p>This image is created from a gv-file. I saved it as fsm.gv:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>digraph finite_state_machine { rankdir=LR; size=&quot;8,5&quot; node [shape = doublecircle]; S; node [shape = point ]; qi node [shape = circle]; qi -&gt; S; S -&gt; q1 [ label = &quot;a&quot; ]; S -&gt; S [ label = &quot;a&quot; ]; q1 -&gt; S [ label = &quot;a&quot; ]; q1 -&gt; q2 [ label = &quot;b&quot; ]; q2 -&gt; q1 [ label = &quot;b&quot; ]; q2 -&gt; q2 [ label = &quot;b&quot; ]; } </pre></div> </div> </div> <p>To create a graph (or the picture of the nondeterministic finite-state machine) you have to enter the following command in Ubuntu Linux:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>dot -Tpng fsm.gv -o myFiniteStateMachine.png </pre></div> </div> </div> <h2>Deterministic finite-state machine</h2> <div style="width: 538px" class="wp-caption aligncenter"><a href="../images/2011/10/deterministic-finite-state-machine.png"><img src="../images/2011/10/deterministic-finite-state-machine.png" alt="Deterministic finite-state machine" width="" height="" class="size-full wp-image-8171" /></a><p class="wp-caption-text">Deterministic finite-state machine</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>digraph finite_state_machine { rankdir=LR; size=&quot;8,5&quot; node [shape = doublecircle, label=&quot;{f}&quot;, fontsize=12] f; node [shape = doublecircle, label=&quot;{q2, f}&quot;, fontsize=10] q2f; node [shape = circle, label=&quot;S&quot;, fontsize=14] S; node [shape = circle, label=&quot;{q1}&quot;, fontsize=12] q1; node [shape = circle, label=&quot;{q2}&quot;, fontsize=12] q2; node [shape = point ]; qi qi -&gt; S; S -&gt; q1 [ label = &quot;a&quot; ]; S -&gt; q2f [ label = &quot;b&quot; ]; S -&gt; q2 [ label = &quot;c&quot; ]; q1 -&gt; q2 [ label = &quot;b&quot; ]; q2f -&gt; f [ label = &quot;b&quot; ]; q2f -&gt; q2 [ label = &quot;c&quot; ]; q2 -&gt; f [ label = &quot;b&quot; ]; q2 -&gt; q2 [ label = &quot;c&quot; ]; } </pre></div> </div> </div> <h2>LaTeX</h2> <p>If you want to draw finite-state machines with LaTeX, you might want to give <a href="http://www.texample.net/tikz/examples/feature/automata-and-petri-nets/">tikz</a> a try.</p> <p>This is the most minimalistic version I could create. It is equivalent to the nondeterministic finite-state machine I’ve described above:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{scrartcl} \usepackage{tikz} \usetikzlibrary{arrows,automata} \begin{document} \begin{tikzpicture}[&gt;=stealth',shorten &gt;=1pt,auto,node distance=2cm] \node[initial,state,accepting] (S) {$S$}; \node[state] (q1) [right of=S] {$q_1$}; \node[state] (q2) [right of=q1] {$q_2$}; \path[-&gt;] (S) edge [loop above] node {a} (S) edge node {a} (q1) (q1) edge [bend left] node {a} (S) edge node {b} (q2) (q2) edge [loop above] node {b} (q2) edge [bend left] node {b} (q1); \end{tikzpicture} \end{document} </pre></div> </div> </div> <p>This was the most basic example which shows how to draw a finite-state automaton with LaTeX. You can get it as a PDF with this command:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>pdflatex latexsheet.tex -output-format=pdf </pre></div> </div> </div> <p>If you want to see some more fancy stuff, take a look at this example of a non-deterministic finite state machine:</p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/latex-finite-state-machine.png"><img src="../images/2011/10/latex-finite-state-machine.png" alt="Finite-state-machine with LaTeX" width="" height="" class="size-full wp-image-13421" /></a><p class="wp-caption-text">Finite-state-machine with LaTeX</p></div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{scrartcl} \usepackage{tikz} \usetikzlibrary{arrows,automata} \begin{document} \begin{tikzpicture}[&gt;=stealth',shorten &gt;=1pt,auto,node distance=2cm] \node[initial,state,accepting] (S) {$S$}; \node[state] (q1) [right of=S] {$q_1$}; \node[state] (q2) [right of=q1] {$q_2$}; \path[-&gt;] (S) edge [loop above] node {a} (S); \path[-&gt;, dashed] (S) edge node {a} (q1); \path[-&gt;, dotted] (q1) edge [bend left] node {a} (S); \path[-&gt;&gt;, dotted] (q1) edge node {b} (q2); \path (q2) edge [loop above] node {b} (q2) edge [bend left] node {b} (q1); \end{tikzpicture} \end{document} </pre></div> </div> </div> <h3>Markov models</h3> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass{scrartcl} \usepackage{tikz} \usetikzlibrary{arrows,automata} \begin{document} \begin{tikzpicture}[-&gt;,&gt;=stealth',shorten &gt;=1pt,node distance=2.8cm] % When you want to use // inside of nodes, you have to algin \tikzstyle{every state}=[align=center] \node[state,initial,label=below:Start] (Start) {A 0.6\\B 0.2\\C 0.2}; \node[state,label=below:Mitte] (Mitte) [right of=Start] {A 0.1\\B 0.1\\C 0.8}; \node[state,label=below:Ende] (Ende) [right of=Mitte] {A 0.5\\B 0.2\\C 0.3}; \path (Start) edge node[above] {0.2} (Mitte); \path (Mitte) edge node[above] {0.8} (Ende); \path (Start) edge [loop above] node {0.8} (Start); \path (Mitte) edge [loop above] node {0.2} (Mitte); \path (Ende) edge [loop above] node {1} (Ende); \end{tikzpicture} \end{document} </pre></div> </div> </div> <h2>Further Reading</h2> <ul> <li><a href="http://www.graphviz.org/doc/info/shapes.html">DOT Node Shape reference</a></li> <li><a href="http://wiki.ubuntuusers.de/Graphviz">ubuntuusers.de</a> (German): Installation on Ubuntu</li> <li><a href="http://www.wikischool.de/wiki/WikiSchool:Graphviz">Wikischool.de</a> (German): Many examples</li> </ul> DVD menu in YouTube //martin-thoma.com/dvd-menu-in-youtube/ Fri, 28 Oct 2011 19:25:46 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/dvd-menu-in-youtube <p>Today a friend of mine <a href="http://www.rene-pickhardt.de/first-youtube-dvd-online-for-ballads-n-bullets-by-in-legend/">posted</a> an article about a very neat idea. He created a DVD-like menu with several YouTube clips.</p> <p>Just take a look:</p> <iframe width="560" height="315" src="http://www.youtube.com/embed/lSZNskw1AVw?rel=0" frameborder="0" allowfullscreen=""></iframe> <p>This idea is beatiful: It is simple, but it didn’t come to my mind before. I knew overlays and saw them sometimes, but I never saw them being used in such a nice way.</p> <p>Great work, René!</p> Einführung in die abzählende Kombinatorik //martin-thoma.com/einfuhrung-in-die-abzahlende-kombinatorik/ Mon, 24 Oct 2011 20:53:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/einfuhrung-in-die-abzahlende-kombinatorik <p>Die abzählende Kombinatorik beschäftigt sich mit der Bestimmung der Anzahl möglicher Anordnungen oder Auswahlen.</p> <h2>Begriffe</h2> <h3>Permutation</h3> <p>Eine Permutation ist eine Veränderung der Reihenfolge einer geordneten Anzahl von Objekten. <small>(Weil die Objekte in irgend einer Art geordnet sein müssen, damit sich eine Reihenfolge ändern kann, will ich diese Ansammlung nicht “Menge” nennen.)</small></p> <p>Beispiel: Wir haben eine Liste von Zahlen: [1, 2, 5, -7, -1, 3] Eine Permutation davon ist: [1, 2, 5, -7, 3, -1]</p> <p>Anagramme sind Permutationen: “ANGSTBUDE” und “BUNDESTAG”</p> <p>Das Wesentliche ist also, dass es bei Permutationen auf die Reihenfolge ankommt.</p> <h3>k-Permutation</h3> <p>Eine k-Permutation wählt aus n Objekten k aus.</p> <p>Wenn wir also die 6 Objekte [1, 2, 5, -7, -1, 3] haben, wären [1, 2, 5], [5, 2, 1], [-7, 2, 3] und [-7, 3, 3] verschiedene 3-Permutationen davon.</p> <h3>Kombination und k-Kombination</h3> <p>Bei einer Kombination kommt es <em>nicht</em> auf die Reihenfolge an. Sonst ist alles analog zu den Permutationen.</p> <h2>Formeln</h2> <p>Es gibt nur vier Formeln, die man sich merken sollte. Dabei sei n die Anzahl aller wählbaren Objekte:</p> <table> <tr><th>&nbsp;</th><th>mit Wiederholungen</th><th>ohne Wiederholungen</th></tr> <tr><th>k-Permutation</th><td>`$n^k$`</td><td>`$\frac{n!}{(n-k)!}$`</td></tr> <tr><th>k-Kombination</th><td>`$\binom{n-1+k}{k}$`</td><td>`$\binom{n}{k}$`</td></tr> </table> <p>Warum stimmt das?</p> <p>Wenn man n Objekte hat und k-mal eines davon auswählt, wobei die Reihenfolge eine Rolle spielt und man das Objekt danach immer wieder zurück legt (also Wiederholungen haben kann), dann hat man beim ersten mal n verschiedene Wahlmöglichkeiten. Beim zweiten, dritten, … k.-Zug auch. Es sind also <code>$\underbrace{n \cdot n \cdot ... \cdot n}_\text{k mal} = n^k$</code> Möglichkeiten.</p> <p>Wenn man die Objekte nicht wieder zurück legt, die Reihenfolge aber eine Rolle spielt, hat man beim ersten Zug wieder n Möglichkeiten. Beim zweiten Zug sind es (n-1), beim dritten (n-3), … beim k.-Zug (n-k+1) Möglichkeiten. Also gilt: <code>$\underbrace{(n-0) \cdot (n-1) \cdot ... \cdot (n- (k-1))}_\text{k Faktoren} = \prod_{i=0}^{k-1} (n-i)= \frac{n!}{(n-k)!}$</code></p> <p>Angenommen es spielt nun nur eine Rolle, welche Objekte man ausgewählt hat, aber nicht wann. Dann gibt es, wenn man die Objekte nicht wieder zurücklegt, <code>$\frac{n!}{(n-k)!}$</code> Möglichkeiten, abzüglich der Möglichkeiten, die nur bei Beachtung der Reihenfolge eine Rolle spielen. Das bedeutet, es muss noch durch k! geteilt werden. Das kann man sich klar machen, indem man eine bestimmte Menge an k ausgewählten Objekten betrachtet. Dann muss man entscheiden, welches das erste ist. Dafür gibt es k Möglichkeiten. Für das zweite hat man (k-1) Möglichkeiten, usw. Das Bedeutet, es gibt für diesen Fall <code>$\frac{n!}{(n-k)! \cdot k!} = \binom{n}{k}$</code> Möglichkeiten.</p> <p>Der schwerste Fall sind k-Kombinationen mit zurücklegen. Dafür denkt man sich am besten, dass man eine Liste der Objekte hat. Nun macht man, um die n Objekte zu trennen, zwischen diese (n-1) Sternchen. Die Anzahl wird durch k Striche repräsentiert. Nun kann man sich fragen, wie viele Möglichkeiten es gibt diese k Striche und (n-1) Sternchen anzuordnen. Das sind, wenn man die k Striche auf (n-1)+k Plätze verteilt: <code>$\frac{(n-1+k)!}{(n-1)!} \cdot \underbrace{\frac{1}{k!}}_\text{Reihenfolge ist egal} = \frac{(n-1+k)!}{(n-1)!k!}$</code></p> <p>Dies entspricht genau dem Binomialkoeffizienten: <code>$\binom{n-1+k}{k} = \frac{(n-1+k)!}{k!((n-1+k)-k)!} = \frac{(n-1+k)!}{k!(n-1)!}$</code></p> <h2>Siehe auch</h2> <p>Wikipedia:</p> <ul> <li><a href="http://de.wikipedia.org/wiki/Kombinatorik">Kombinatorik</a> (Der Artikel ist leider sehr mager. Eventuell hat jemand lust ihn zu erg&auml;nzen?)</li> <li><a href="http://de.wikipedia.org/wiki/Abz%C3%A4hlende_Kombinatorik">Abz&auml;hlende Kombinatorik</a></li> <li><a href="http://de.wikipedia.org/wiki/Permutation">Permutation</a></li> <li><a href="http://de.wikipedia.org/wiki/Anagramm">Anagramm</a></li> <li><a href="http://de.wikipedia.org/wiki/Binomialkoeffizient">Binomialkoeffizient</a></li> </ul> Clip: Love Tap //martin-thoma.com/clip-love-tap/ Sun, 23 Oct 2011 16:27:19 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/clip-love-tap <iframe src="http://player.vimeo.com/video/18486821?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" allowfullscreen=""></iframe> <p>A five-minute reminder to not let love pass you by. Developed as original content for Walt Disney Pictures Short Films division.</p> Wie führe ich einen sauberen Beweis? //martin-thoma.com/wie-fuhre-ich-einen-sauberen-beweis/ Sun, 23 Oct 2011 13:07:29 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/wie-fuhre-ich-einen-sauberen-beweis <p>In der Mathematik spielen Beweise eine zentrale Rolle. Es gibt verschiedene Beweisarten, aber im folgenden will ich nur einen direkten Beweis führen. Dieses Beispiel wurde in der Übung zu Analysis I von Herrn Bolleyer gemacht.</p> <h2>Gliederung</h2> <p>Beweise kann man in drei Teile gliedern:</p> <p><strong>Voraussetzungen</strong>: Hier werden spezielle Objekte, die im Beweis benötigt werden, definiert.</p> <p><strong>Behauptung</strong>: Die Behauptung stellt eine Aussage über die Objekte in der Voraussetzung auf. Sie kann sehr kurz sein.</p> <p><strong>Beweis</strong>: Der Beweis zeigt durch eine folge von logischen Schlussfolgerungen aus den Voraussetzungen, dass die Behauptung wahr ist.</p> <p>Nötig ist manchmal nur die Behauptung und der Beweis. Mit der Vorraussetzung ist der Beweis zwar vollständig, allerdings würde ich vor dem eigentlichem Beweis eine <strong>Beweisidee</strong> begrüßen. Die Beweisidee kann sehr kurz sein. Das ist der eine Satz, der einem Studenten, der sich mit der Aussage beschäftigt hat, sagt wie sie zu lösen ist.</p> <h2>Beispiel eines direkten Beweises</h2> <p><strong>Voraussetzung</strong>: Sei <code>$M = \{ x \in \mathbb{R}: |x-3| \lt 2 \}$</code></p> <p><strong>Behauptung</strong>: <code>$M = (1,5)$</code></p> <p><strong>Beweis</strong>: Per Definition gilt: <code>$|x-3| : = \left \{ \begin{array}{ll} x &amp; \text{, falls } x \geq 3 \\ -(x-3) &amp; \text{, falls } x \lt 3 \end{array} \right.$</code></p> <p><code>$ M = \{x \in \mathbb{R} \lt 2 \} = \underbrace{\{x \in \mathbb{R} : |x-3| \lt 2 \land x \geq 3 \}}_{M_1} \cup \underbrace{\{x \in \mathbb{R}: |x -3| \lt 2 \land x \lt 3\}}_{M_2}$</code></p> <p>Betrachte <code>$M_1$</code>: <code>$ x\in M_1 \Leftrightarrow |x-3| \lt 2 \land x \geq 3$</code> <code>$\Leftrightarrow x-3 \lt 2 \land x \geq 3$</code> <code>$\Leftrightarrow x \lt 5 \land x \geq 3$</code> <code>$\Leftrightarrow 3 \leq x \lt 5$</code> Also gilt <code>$M_1 = [3, 5)$</code></p> <p>Betrachte <code>$M_2$</code>: <code>$ x\in M_2 \Leftrightarrow |x-3| \lt 2 \land x \lt 3$</code> <code>$\Leftrightarrow -(x-3) \lt 2 \land x \lt 3$</code> <code>$\Leftrightarrow -x + 3 \lt 2 \land x \lt 3$</code> <code>$\Leftrightarrow 1 \lt x \land x \lt 3$</code> <code>$\Leftrightarrow 1 \lt x \lt 3$</code> Also gilt <code>$M_2 = (1,3)$</code></p> <p>Es gilt <code>$M = M_1 \cup M_2 = [3, 5) \cup (1,3) = (1,5)$</code> q.e.d.</p> <h2>Weitere Beweisformen</h2> <p>Der <a href="../wie-fuhre-ich-einen-induktionsbeweis/">Induktionsbeweis</a> ist sehr nützlich, wenn man eine Aussage für Elemente zeigen muss, die einen festen Abstand haben. Also z.B. eine Aussage für die Natürlichen Zahlen oder die ganzen Zahlen.</p> <p>Der <a href="../pumping-lemma/">Widerspruchsbeweis</a> ist gut geeignet, wenn notwendige, aber nicht hinreichende Kriterien für das Gegenteil der Behauptung nicht erfüllt sind.</p> <h2>Siehe auch</h2> <ul> <li>Wikipedia: <a href="http://de.wikipedia.org/wiki/Beweis_(Mathematik)">Beweis</a></li> <li><a href="http://mitschriebwiki.nomeata.de/WS07/Ana1.pdf">Inoffizielles Script</a></li> </ul> Game: Marble Run //martin-thoma.com/game-marble-run/ Sun, 23 Oct 2011 08:41:58 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/game-marble-run <div style="width: 594px" class="wp-caption alignleft"><a href="../images/2011/10/marblerun.png"><img src="../images/2011/10/marblerun.png" alt="Marble Run" width="" height="" class="size-full wp-image-7181" /></a><p class="wp-caption-text">Marble Run</p></div> <p><b>Go to the Game</b>: <a href="http://marblerun.at/tracks/new" rel="nofollow">marblerun.at</a> <b>Task</b>: Create a Track for that little red dot, which is as long as possible. <b>How to play</b>: On the right side of the screen you can see a toolbar. Different bricks, some with special functions, can be used to build your track. <b>My Record</b>: 37m <b>Programming</b>: The entire page is written in HTML + JavaScript. They used the Prototype JS library.</p> Understanding Python Lists //martin-thoma.com/understanding-python-lists/ Sat, 22 Oct 2011 23:01:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/understanding-python-lists <p>This article is about Python lists. I just want to show you some examples of the unexpected behaviour (for non-python-programmers) of lists in Python.</p> <p>Imagine you have the following Python source code:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#!/usr/bin/python</span> <span class="c"># -*- coding: utf-8 -*-</span> <span class="kn">import</span> <span class="nn">copy</span> <span class="n">example1</span> <span class="o">=</span> <span class="p">[[</span><span class="mi">1</span><span class="p">,</span><span class="mi">5</span><span class="p">,</span><span class="mi">7</span><span class="p">],[</span><span class="mi">3</span><span class="p">,</span><span class="mi">6</span><span class="p">],[],</span> <span class="p">[</span><span class="mi">8</span><span class="p">,</span><span class="mi">1</span><span class="p">,</span><span class="mi">6</span><span class="p">]]</span> <span class="n">example2</span> <span class="o">=</span> <span class="n">example1</span><span class="p">[:]</span> <span class="n">example3</span> <span class="o">=</span> <span class="nb">list</span><span class="p">(</span><span class="n">example1</span><span class="p">)</span> <span class="n">example4</span> <span class="o">=</span> <span class="n">copy</span><span class="o">.</span><span class="n">deepcopy</span><span class="p">(</span><span class="n">example1</span><span class="p">)</span> <span class="n">example1</span><span class="p">[</span><span class="mi">1</span><span class="p">][</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="mi">0</span> <span class="n">example1</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span> <span class="k">print</span> <span class="n">example1</span> <span class="k">print</span> <span class="n">example2</span> <span class="k">print</span> <span class="n">example3</span> <span class="k">print</span> <span class="n">example4</span></code></pre></div> <p>How should the output look like? Think about it a second, then scroll down.</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="o">[[</span>1,5,7<span class="o">]</span>,<span class="o">[</span>0,6<span class="o">]</span>,<span class="o">[]</span>,<span class="o">[</span>8,1,6<span class="o">]</span>,1<span class="o">]</span> <span class="o">[[</span>1,5,7<span class="o">]</span>,<span class="o">[</span>0,6<span class="o">]</span>,<span class="o">[]</span>,<span class="o">[</span>8,1,6<span class="o">]]</span> <span class="o">[[</span>1,5,7<span class="o">]</span>,<span class="o">[</span>0,6<span class="o">]</span>,<span class="o">[]</span>,<span class="o">[</span>8,1,6<span class="o">]]</span> <span class="o">[[</span>1,5,7<span class="o">]</span>,<span class="o">[</span>3,6<span class="o">]</span>,<span class="o">[]</span>,<span class="o">[</span>8,1,6<span class="o">]]</span></code></pre></div> <p>The reason for this strange behaviour is how lists are handled in Python. The variable itself is basically only the pointer to the list. If you slice the list (myList[:]) you copy each value of the list into another list. If myList was a nested list, it contained the pointers to the sublists. So, if you want to make a deep copy, you have to use the copy module.</p> <h2>Scoping</h2> <p>phimuemue added this example in my old blog:</p> <p>Another issue I ran into concerns the scoping of Python:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">i</span><span class="o">=</span><span class="mi">0</span> <span class="p">[</span><span class="n">i</span> <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span><span class="mi">2</span><span class="p">,</span><span class="mi">3</span><span class="p">]]</span> <span class="k">print</span> <span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="c"># yields 3</span></code></pre></div> <p>That means, python doesn’t create a new variable for the list comprehension but uses the outer i.</p> <h2>Recursive Lists</h2> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="n">a</span> <span class="o">=</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">]</span> <span class="n">b</span> <span class="o">=</span> <span class="p">[</span><span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">6</span><span class="p">]</span> <span class="n">a</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="p">[</span><span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">6</span><span class="p">]]</span> <span class="n">b</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="n">b</span><span class="p">)</span> <span class="p">[</span><span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">6</span><span class="p">,</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="p">[</span><span class="o">...</span><span class="p">]]]</span> <span class="k">print</span><span class="p">(</span><span class="n">a</span><span class="p">)</span> <span class="p">[</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">,</span> <span class="p">[</span><span class="mi">4</span><span class="p">,</span> <span class="mi">5</span><span class="p">,</span> <span class="mi">6</span><span class="p">,</span> <span class="p">[</span><span class="o">...</span><span class="p">]]]</span></code></pre></div> <p>Do you know more examples of unexpected behaviour of python lists? Please share them in the comments!</p> Improvements for my University's Website //martin-thoma.com/improvements-for-my-universitys-website/ Sat, 22 Oct 2011 20:55:05 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/improvements-for-my-universitys-website <p>I am now studying at the <a href="http://en.wikipedia.org/wiki/Karlsruhe_Institute_of_Technology">Karlsruhe Institute of Technology</a> (KIT). Although I think that the Websites of KIT is much better than the Website of most Universities, I can imagine several possibilities how the online services could be improved:</p> <h2>Use OpenID</h2> <p>I have 9 different accounts with 7 different passwords for university. After my first week.</p> <p>I guess it is impossible to use the same login system for all services of the university as we have many different teams of developers. But it is easily possible to get an OpenID provider. The students could have an URL like student.kit.edu/openid/u…. or something similar. The login would always happen at one place and this server could tell the other services that the right user is trying to get access.</p> <p>Some more information about OpenID is here:</p> <ul> <li><a href="http://en.wikipedia.org/wiki/OpenID">Wikipedia</a> (the <a href="http://de.wikipedia.org/wiki/OpenID">German article</a> is much better)</li> <li><a href="http://www.youtube.com/watch?v=xcmY8Pk-qEk">OpenID According to Dave</a> (4:35 min)</li> <li><a href="http://www.youtube.com/watch?v=DslTkwON1Bk">The Implications of OpenID</a> (51:19 min)</li> </ul> <h2>Customization</h2> <p>It would help me a lot if I could customize my start page at studium.kit.edu by adding some links / text.</p> <h2>Consistency</h2> <p>The university was called “University of Karlsruhe” (“Universität Karlsruhe” in German) a few years ago. Then they thought it was time to rename the university as they made major structural changes.</p> <h3>URLs - one Top-level domain</h3> <p>They also got a new URL. Before the new one is kit.edu, but it seems as if many pages were still on the old <abbr title="top-level domain">TLD</abbr>:</p> <ul> <li>uni-karlsruhe.de: <ul> <li><a href="http://www.fsmi.uni-karlsruhe.de/">fsmi.uni-karlsruhe.de</a>: fsmi.kit.edu</li> <li><a href="http://www2.mach.uni-karlsruhe.de/srmach/srmach.php">mach.uni-karlsruhe.de</a>: should be mach.kit.edu</li> </ul> <li>http://www.ira.uka.de/: <a href="https://webinscribe.ira.uka.de/">webinscribe.ira.uka.de</a>: should be webinscribe.kit.edu. Additionally, a link from studium.kit.edu to this service should be created.</li> <li><a href="http://www.itas.fzk.de/">www.itas.fzk.de</a>: should be itas.kit.edu. (I guess fzk means "Forschungszentrum Karlsruhe" - research center Karlsruhe)</li> This could be fixed with the following steps: <ul> <li>Find old URLs / Links (e.g. with <bbr title="Regular Expressions">RegEx and a <a href="http://en.wikipedia.org/wiki/Web_crawler">crawler</a>) <li>Introduce the new URL by one of those two possibilites: <ul> <li>Make HTML-redirections for the new ones (e.g. from fsmi.kit.edu to www.fsmi.uni-karlsruhe.de)</li> <li>Move the content from the old space to the new space. Make sure that nothing breaks by adding a <a href="http://en.wikipedia.org/wiki/List_of_HTTP_status_codes#3xx_Redirection">301 status code</a>.</li> </ul> <li>Replace all links to the old URL by the new URL.</li> <li>Wait at least one, rather two semester. Check which internal Websites still use the old URL and try to fix those links.</li> <li>Completely remove the old URL</li> <h3>Services in one place</h3> KIT offers quite a lot of online services, such as <ul> <li><a href="http://www.bibliothek.kit.edu/cms/index.php">Search for books</a> in KIT-library <li><a href="https://www.rz.uni-karlsruhe.de/cgi-bin/bvprint">bvprint</a>: How much money is left on my printing-account?</li> <li>Webmail: <ul> <li>u....@student.kit.edu / prename.lastname@student.kit.edu / u....@stud.uni-karlsruhe.de: <a href="https://owa.kit.edu">owa.kit.edu</a> - with Microsofts <a href="http://en.wikipedia.org/wiki/Outlook_Web_App">OWA</a></li> <li>s_...@atis.uka.de: <a href="https://webmail.ira.uni-karlsruhe.de/imp/login.php">webmail.ira.uni-karlsruhe.de</a> - with <a href="http://en.wikipedia.org/wiki/Horde_(software)">Horde Groupware</a></li> </ul> </li> <li><a href="http://www.scc.kit.edu/dienste/3203.php">Web-Server</a> with <a href="http://www.scc.kit.edu/dienste/7881.php">MySQL databases</a> and <a href="https://www.rz.uni-karlsruhe.de/phpmyadmin/?server=5">phpMyAdmin</a></li> <li><a href="http://www.scc.kit.edu/dienste/3203.php">New Sites</a>: Create a site for you</li> For some services you need to login via <a href="https://vpn.kit.edu/">https://vpn.kit.edu</a>: <ul> <li>Print preview: <a href="https://scc-print.scc.kit.edu/cgi-bin/preview/index.cgi?printer=bw600dpi&amp;user=">https://scc-print.scc.kit.edu</a> and the (buggy) <a href="https://scc-print-06.scc.kit.edu/cgi-bin/print/index.cgi">newer version</a>.</li> <li><a href="https://print.rz.uni-karlsruhe.de/cgi-bin/pu">PrintUtil</a>: Which jobs are in the queue of the printer?</li> <li>Scanning: <a href="http://studscan.ira.uka.de/">studscan.ira.uka.de</a></li> </ul> I had to search for some services, like a SVN-Repository (<a href="http://www.atis.uka.de/1422.php">How do I get a SVN repository at KIT?</a>) The important services should be available at studium.kit.edu. I think this would be a link to the Webmail, to the printing services and webinscribe. <h2>Help the user to find what he needs</h2> <h3>Redundancy</h3> Sometimes it is good to provide several alternatives. I have one example: One of the most important URLs at my university's website is studium.kit.edu. In the first week, I typed quite often student.kit.edu. Google corrected kit to mit and the MIT has such a page. I think it would be a good idea to look at the 404-error log and check, if this occurs often. If it does, a redirect should probable be added. All redundant URLs should point to ONE target, of course. It's best to use a 301 redirection. <h3>Short, but meaningful URLs</h3> At the moment KIT makes use of such URLs: <ul> <li>www.kit.edu/index.php should be kit.edu</li> <li>www.informatik.kit.edu/index.php should be informatik.kit.edu</li> <li><a href="http://www.informatik.kit.edu/883.php">www.informatik.kit.edu/883.php</a> should be informatik.kit.edu/informatik-bachelor</li> <li>www.informatik.kit.edu/interact.php should be informatik.kit.edu/interact</li> </ul> This can be done by modifying the .htaccess-file (for the decision to redirect calls prefixed with www to a non-www page). In many cases you can use the URL which I would prefer, but you're redirected to the other one. This means if a professor is copying the ugly link to his presentation, all students will have to write it down. <h3>Helpfull 404 Page</h3> At the moment I get only: "404 NOT FOUND". This is not very helpful. You should provide a <a href="../custom-404-error-pages/" title="Custom 404 error pages">custom 404 error page</a>. <h3>Use Feeds</h3> I would like to get the latest news about KIT, but I don't want to search for it. I also don't want to look at the homepage of KIT to check if I know the latest content. This should be done with a RSS feed. The start page should have an auto-detectable RSS-Feed. It can be added with the following HTML-Tag in the head-section of the document: ```html <link rel="alternate" type="application/rss+xml" title="KIT News Feed" href="/rss/" /> ``` <h2>Use HTML5 input tags</h2> HTML5 input tags can much more than the old ones. You can define <a href="http://www.w3schools.com/html5/att_input_autofocus.asp">autofocus</a> for the first element, <a href="http://www.w3schools.com/html5/att_input_placeholder.asp">placeholders</a>, <a href="http://www.w3schools.com/html5/att_input_autocomplete.asp">autocomplete</a>=off for password fields at the registration, <a href="http://www.w3schools.com/html5/att_input_pattern.asp">patterns</a> for clients side validation and <a href="http://www.w3schools.com/html5/att_input_type.asp">much more types</a> than text and password. Old browsers automatically fall back into a simple text input field. Examples for pages that could be improved: <ul> <li><a href="http://kit.edu">kit.edu</a>: Add <a href="../search-engine-autodiscovery/" title="Search Engine Autodiscovery">search engine autodiscovery</a></li> <li><a href="http://i3vloan.ubka.uni-karlsruhe.de/19466917473783462330/i3v_library/ausleihe/i3v_ausleihe.cgi?opacdb=UBKA_OPAC&amp;session=19466917473783462330&amp;Funktion=Ersterfassung&amp;lang=DE">Register library account</a></li> <li><a href="https://studium.kit.edu">studium.kit.edu</a></li> <li><a href="http://www.kit.edu/index.php">kit.edu</a> (the search box)</li> <li><a href="http://www.kit.edu/studieren/6243.php">kit.edu/studieren/6243.php</a> (the contact form at the bottom)</li> <li><a href="http://www.kit.edu/markt/userlogin.php">kit.edu/markt/userlogin</a> (the login form)</li> </ul> If somebody had much free time he could try to get valid HTML5 for the whole website. This isn't really helpful for the user (by now), but it would be nice to have a standard conform website. <h2>Payments</h2> You have to pay with the "KIT-Card" for meals in the cafeteria and if you want to print something. But you have to transfer the money to the printing account from your cafeteria account, before you can print anything. This seems to be not logical for me. Why do we have to use two university "bank" accounts? </li></ul></li></bbr></li></ul></li></ul> Custom 404 error pages //martin-thoma.com/custom-404-error-pages/ Sat, 22 Oct 2011 20:50:47 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/custom-404-error-pages <p><a href="../images/2011/10/404-Not-Found.png"><img src="../images/2011/10/404-Not-Found.png" alt="" title="404 Not Found" width="128" height="128" class="alignleft size-full wp-image-7061" /></a> A 404 http status code means that no document could be found at the given URL. The reason could be a misspelled URL or moved content.</p> <p>Anyway, the user needs help now. The standard error page doesn’t provide much information, so you should create a custome one.</p> <p>If you like more information, just google for “custom 404 page”.</p> <h2>How to create a custom 404 error page</h2> <p>Simply add the following line to your .htaccess file:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>ErrorDocument 404 /notfound.php </pre></div> </div> </div> <p>(This will work only on an Apache webserver, of course).</p> <p>Now you have to create a notfound.php file. This file should provide the following information:</p> <ul> <li>Tell the user that he typed a wrong URL or that the link pointed to a target which doesn't exist</li> <li>Provide a search box</li> <li>Provide a link to a graphical sitemap</li> <li>Provide some funny / interesting content</li> <li>Make sure that a 404 http status code is still returned after your changes</li> </ul> <h2>Good examples</h2> <ul> <li><a href="http://www.hongkiat.com/blog/60-really-cool-and-creative-error-404-pages/">60 Really Cool And Creative Error 404 Pages</a></li> <li><a href="http://dzineblog.com/2008/11/custom-error-404-pages.html">36 Cool Custom Error 404 Pages</a></li> <li><a href="http://www.smashingmagazine.com/2007/08/17/404-error-pages-reloaded/">404 Error Pages: Reloaded</a></li> </ul> <h2>Further Reading</h2> <ul> <li><a href="http://www.404errorpages.com/">404 Error Pages .com</a></li> <li><a href="http://en.wikipedia.org/wiki/HTTP_404">Wikipedia</a></li> </ul> Search Engine Autodiscovery //martin-thoma.com/search-engine-autodiscovery/ Sat, 22 Oct 2011 11:12:07 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/search-engine-autodiscovery <p>Recently I read a very good post about search engine autodiscovery <a href="http://www.knallisworld.de/blog/2011/04/14/autodiscovery-der-searchengine-in-google-chrome-opensearch/">by Jan Phillip</a>. Did you know that many browsers can detect an internal search engine automatically? Firefox gives you the possibility to add such a search engine to your browser:</p> <div style="width: 304px" class="wp-caption aligncenter"><a href="../images/2011/10/firefox-add-search-engine.png"><img src="../images/2011/10/firefox-add-search-engine.png" alt="Firefox: Add search engine detected via autodiscovery" width="" height="" class="size-full wp-image-6921" /></a><p class="wp-caption-text">Firefox: Add search engine detected via autodiscovery</p></div> <h2>OpenSearch</h2> <p><a href="http://en.wikipedia.org/wiki/OpenSearch">OpenSearch</a> is a collection of technologies. This project aims to create a standard for publishing the metadata which describes a search engine: name, description, URL-pattern, language, …</p> <p>A <abbr title="OpenSearch Description Document">OSSD</abbr> looks like this: ```xml</p> <opensearchdescription xmlns="http://a9.com/-/spec/opensearch/1.1/"> <shortname>Example</shortname> <description>My example search engine</description> <inputencoding>UTF-8</inputencoding> <image height="16" width="16" type="image/x-icon"> http://example.org/favicon.ico </image> <url type="text/html" template="http://example.org/index.html#search={searchTerms}" /> </opensearchdescription> <pre><code> The browser needs a hint where it can find the OSSD. So you have to add the following tag to your website: ```xml &lt;link title = "Example" type = "application/opensearchdescription+xml" rel = "search" href = "http://example.org/opensearch.xml"&gt; </code></pre> <p>Now you can add the websites internal search engine automatically to Chrome and easily to Firefox and Internet Explorer 8+.</p> <p>Additionally, you can add this little piece of JavaScript to tell Firefox 2+ and Internet Explorer 7+ that your site supports OpenSearch:</p> <div class="highlight"><pre><code class="language-javascript" data-lang="javascript"><span class="nb">window</span><span class="p">.</span><span class="nx">external</span><span class="p">.</span><span class="nx">AddSearchProvider</span><span class="p">(</span><span class="s2">&quot;http://exampl.org/opensearch.xml&quot;</span><span class="p">);</span></code></pre></div> <h2>Google Chrome Autodiscovery</h2> <p>Google doesn’t provide a <abbr title="user interface">UI</abbr> for adding an internal search engine. Instead, you can add it via Settings:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/google-chrome-add-search-300x206.png"><img src="../images/2011/10/google-chrome-add-search-300x206.png" alt="Add Search Engines via Settings in Google Chrome" width="" height="" class="size-medium wp-image-6891" /></a><p class="wp-caption-text">Add Search Engines via Settings in Google Chrome</p></div> <p>Chrome also adds the sites internal search engine automatically. Did you ever notice this? Here are some screenshots:</p> <div style="width: 669px" class="wp-caption aligncenter"><a href="../images/2011/10/google-chrome-search-1.png"><img src="../images/2011/10/google-chrome-search-1.png" alt="Google Chrome Search - Hit tab to search this site" width="" height="" class="size-full wp-image-6841" /></a><p class="wp-caption-text">Google Chrome Search - Hit tab to search this site</p></div> <div style="width: 666px" class="wp-caption aligncenter"><a href="../images/2011/10/google-chrome-search-2.png"><img src="../images/2011/10/google-chrome-search-2.png" alt="Google Chrome Search - Search with the websites internal search engine" width="" height="" class="size-full wp-image-6851" /></a><p class="wp-caption-text">Google Chrome Search - Search with the websites internal search engine</p></div> <p>Interestingly the auto discovery only works if the search engine is at the homepage. You have to have either an input field of the type <code>search</code> or of the type <code>text</code> with the name <code>s</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;form&gt;</span> <span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">search</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">s</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;/form&gt;</span> </pre></div> </div> </div> <p>or</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;form&gt;</span> <span style="color:#070;font-weight:bold">&lt;input</span> <span style="color:#b48">type</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">text</span><span style="color:#710">&quot;</span></span> <span style="color:#b48">name</span>=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">s</span><span style="color:#710">&quot;</span></span> <span style="color:#070;font-weight:bold">/&gt;</span> <span style="color:#070;font-weight:bold">&lt;/form&gt;</span> </pre></div> </div> </div> <h2>Drawbacks</h2> <ul> <li>It seems as if Safari didn't support OSSD natively. (14.04.2011)</li> <li>Internet Explorer 9 seems not to support OSSD.</li> <li>No support by Opera.</li> </ul> <h2>This article in a nutshell</h2> <ul> <li>opensearch.xml gives meta information about your websites internal search engine</li> <li>For Chromes autodiscovery you will need to add an input fild with "type=search" or "name=s"</li> <li>It is not necessary for Chrome that the user can see the form (display:none with CSS) nor that it the site start page is loaded long (meta redirect after 0 seconds).</li> <li>Adding the search engine manually is possible in almost all browsers</li> <li>With OSSD you can manage more than one internal search engine.</li> </ul> <h2>Further reading</h2> <ul> <li>OpenSearch.org: <ul> <li><a href="http://www.opensearch.org/Community/OpenSearch_search_clients">OpenSearch search clients</a></li> <li><a href="http://www.opensearch.org/Documentation/Developer_best_practices_guide">Developer best practices guide</a></li> </ul> </li> <li>David Walsh: <a href="http://davidwalsh.name/open-search">Add Your Website to Firefox&rsquo;s Search Bar Using OpenSearch XML</a>.</li> </ul> Clip: Bob the Hamster //martin-thoma.com/bob-the-hamste/ Sat, 22 Oct 2011 08:35:27 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/bob-the-hamste <iframe src="http://player.vimeo.com/video/25845008?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" allowfullscreen=""></iframe> <p>Bob tells the story of a little hamster that tries to follow his true love around the globe. Can he catch up? We all hope you have fun watching it! Enjoy!</p> WarLight: An online Risk clone //martin-thoma.com/warlight-an-online-risk-clone/ Fri, 21 Oct 2011 06:36:09 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/warlight-an-online-risk-clone <p><a href="http://en.wikipedia.org/wiki/Risk_(game)">Risk</a> is a great strategic game in which you have to conquer the world.</p> <p>Now I’ve found a clone called “Warlight”:</p> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/Warlight-300x206.png"><img src="../images/2011/10/Warlight-300x206.png" alt="Warlight" width="" height="" class="size-medium wp-image-6511" /></a><p class="wp-caption-text">Warlight</p></div> <p><strong>Go to the Game</strong>: <a href="http://www.kongregate.com/games/FizzerWL/warlight">WarLight</a> on Kongregate <strong>Task</strong>: Conquer the world. <strong>How to play</strong>: Each turn you get armies depending on the number of countries / territories you controll. <strong>My Record</strong>: I could solve Level 1 - 3 and Europe.</p> Community Chess //martin-thoma.com/community-chess/ Wed, 19 Oct 2011 12:30:01 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/community-chess <p>Community Chess is one of my projects. I can make something usefull and play a bit. This project has now an own URL: <a href="http://community-chess.com/">community-chess.com</a></p> <p>It’s a little bit crappy at the moment as I’ve just started studying, but I’ll fix that.</p> <p>If you like to help, please write me an e-mail (info@martin-thoma.de). Everybody can help. Here are some examples:</p> <p>I need some people who</p> <ul> <li>can create a better desing / color scheme</li> <li>use it and know chess rules</li> <li>know how to customize phpBB</li> <li>know how to write Ajax for a better GUI (playChess.php works with PHP and HTML at the moment)</li> <li>can speak other languages than English and German</li> <li>know how to advertise</li> <li>like to support this project with money (I have to pay 26.16 Euro per year for hosting this service. If I get more money I will save it for the next years hosting costs. If it's much more I could try to find a professional designer.)</li> </ul> Analysis I - Teil 1 //martin-thoma.com/analysis-i-teil-1/ Tue, 18 Oct 2011 17:50:21 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/analysis-i-teil-1 <h2>Begriffe und Bezeichnungen</h2> <h3>Mengen</h3> <p>Es seien M und N Mengen.</p> <p><code>$M \cup N$</code>: Vereinigung - Die Elemente sind in M oder N <code>$M \cap N$</code>: Durchschnitt (“Schnittmenge”) - Die Elemente sind in M und N <code>$M \setminus N$</code>: Differenzmenge - Die Elemente sind in M aber nicht in N <code>$M \subseteq N$</code>: Teilmenge - Alle Elemente in M sind auch in N <code>$\emptyset$</code>: Leere Menge <code>$a \in M$</code>: a ist ein Element von M <code>$a \notin M$</code>: a ist kein Element von M</p> <h3>Funktionen</h3> <p>Seien M, N Mengen mit <code>$M \neq \emptyset \neq N$</code>. <code>$f: \underbrace{M}_{\mathbb{D}} \to \underbrace{N}_{\mathbb{W}}$</code></p> <h3>Logische Zeichen</h3> <p><code>$\Rightarrow$</code>: Implikation, z.B. <code>$A \Rightarrow B$</code>: Aus A folgt B <code>$\Leftrightarrow$</code>: Äquivalenz. <code>$A \Rightarrow B \wedge B \Rightarrow A$</code>: Aus A folgt B und umgekehrt. <code>$\underbrace{: \Leftrightarrow}_\text{"genau dann"}$</code>, z.B. <code>$M \subseteq N : \Leftrightarrow \text{aus } x \in M \text{ folgt stets } x \in N$</code>. <code>$\forall$</code>: <a href="http://de.wikipedia.org/wiki/Existenzquantor#Existenz-_und_Allquantor">Allquantor</a>, sprich “für alle” oder “für jedes” <code>$\exists$</code>: <a href="http://de.wikipedia.org/wiki/Existenzquantor#Existenz-_und_Allquantor">Existenzquantor</a>, sprich “es gibt mindestens ein” oder “es existiert”</p> <h2>Reele Zahlen</h2> <p>Die Grundmenge der Analysis ist die Menge <code>$\mathbb{R}$</code>, die Menge der reelen Zahlen. Diese führen wir durch die folgenden 15 Axiome ein.</p> <h3>K&ouml;rperaxiome</h3> <p>In <code>$\mathbb{R}$</code> seien zwei Verknüpfungen “+” und “·” gegeben. Sie ordnen jedem Paar <code>$a, b \in \mathbb{R}$</code> genau ein <code>$ab := a \cdot b \in \mathbb{R}$</code> zu. Dabei soll gelten:</p> <p><code>$\left. \begin{array}{lllll} A.1 &amp; a+ (b+c) &amp; = &amp; (a+b)+c &amp; \forall a, b, c \in \mathbb{R} \\ A.2 &amp; a \cdot (bc) &amp; = &amp; (ab) \cdot c &amp; \forall a, b, c \in \mathbb{R} \\ \end{array} \right \} \text{Assoziativgesetze}$</code></p> <p><code>$\left. \begin{array}{lllll} A.3 &amp; a + b &amp; = &amp; b + a &amp; \forall a, b \in \mathbb{R} \\ A.4 &amp; a \cdot b &amp; = &amp; b) \cdot a &amp; \forall a, b \in \mathbb{R} \\ \end{array} \right \} \text{Kommutativgesetze}$</code></p> <p><code>$\left. \begin{array}{lllll} A.5 &amp; \exists 0 \in \mathbb{R} &amp; : &amp; a + 0 = a &amp; \forall a \in \mathbb{R} \text{ ("Null")} \\ A.6 &amp; \exists 1 \in \mathbb{R} &amp; : &amp; a \cdot 1 = a \wedge 1 \neq 0 &amp; \forall a \in \mathbb{R} \text{ ("Eins")} \\ \end{array} \right \} \text{Neutrales Element}$</code></p> <p><code>$\left. \begin{array}{lllll} A.7 &amp; \forall a \in \mathbb{R} \exists -a \in \mathbb{R} &amp; : &amp; a + (-a) = 0 \\ A.8 &amp; \forall a \in \mathbb{R} \setminus {0} \exists -a^{-1} \in \mathbb{R} &amp; : &amp; a \cdot a^{-1} = 1 \end{array} \right \} \text{Inverses Element}$</code></p> <p><code>$\text{A.9 } a(b+c) = ab+ac \forall a, b, c \in \mathbb{R}$</code>: Distributivgesetz</p> <p>Schreibweisen: für <code>$a, b \in \mathbb{R}: a -b := a + (-b)$</code> für <code>$b \neq 0: \frac{a}{b} := a \cdot b^{-1}$</code></p> <p>Alle Rechenregeln bzgl der Grundrechenarten lassen sich aus A.1 - A.9 herleiten. Diese Regeln seien von nun an bekannt.</p> <p><strong>Behauptung</strong>: Es existiert genau ein <code>$0 \in \mathbb{R}: a+0 = a \forall a \in \mathbb{R}$</code> <strong>Beweis</strong>: Existenz: folgt aus A.5 Eindeutigkeit: Sei <code>$\tilde 0 \in \mathbb{R} \text{ mit }a+\tilde 0 a \forall a \in \mathbb{R}$</code> Mit <code>$a = 0: 0 = 0 + \tilde 0 \underbrace{=}_{\text{A.3}} \tilde 0 + 0 \underbrace{=}_{\text{A.5}} = \tilde 0$</code></p> <p><strong>Behauptung</strong>: Ist <code>$a \in \mathbb{R}\text{, so ist }a \cdot 0 = 0$</code> <strong>Beweis</strong>: <code>$ b := a \cdot 0 \underbrace{\Rightarrow}_\text{A.5} b = a (0 + 0) \Rightarrow a \cdot 0 + a \cdot 0 = b + b$</code> <code>$0 = b + (-b) = (b+b) + (-b) = b + (b + (-b)) = b + 0 = b$</code></p> <h3>Anordnungsaxiome</h3> <p>In <code>$\mathbb{R}$</code> sei eine Relation “<code>$\leq$</code>” gegeben. Dabei soll gelten:</p> <p><code>$ \begin{array}{lll} A.10 &amp; a \leq b \lor b \leq a &amp; \forall a, b \in \mathbb{R} \\ A.11 &amp; a \leq b \land b \leq a &amp; \rightarrow a = b \\ A.12 &amp; a \leq b \land b \leq c &amp; \rightarrow a \leq c \\ A.13 &amp; a \leq b \rightarrow a + c \leq b + c &amp; \forall c \in \mathbb{R} \\ A.14 &amp; a \leq b \land 0 \leq c \Rightarrow a \leq c \end{array} $</code></p> <p>Schreibweise: <code>$a \geq b: \Leftrightarrow b \geq a$</code> <code>$a \lt b: \Leftrightarrow a \leq b \land a \neq b$</code> <code>$a \gt b: \Leftrightarrow b \lt a$</code></p> <p>Alle Regeln für Ungleichungen lassen sich aus A.1 - A.14 herleiten. Diese Regeln seien nun bekannt.</p> <p><strong>Definition</strong>: Für <code>$a \in \mathbb{R}$</code> sei <code>$|a| : = \left \{ \begin{array}{ll} a &amp; \text{, falls } a \geq 0 \\ -a &amp; \text{, falls } a \lt 0 \end{array} \right.$</code></p> <p>Anschaulich: Der Betrag misst den absoluten Abstand zur 0 auf dem Zahlenstrahl.</p> <p><code>$|a-b| \mathrel{\widehat{=}} \text{Abstand von a und b}$</code></p> <p><strong>Satz</strong>: Seien <code>$a, b \in \mathbb{R}$</code>. Dann:</p> <ul> <li>`$|a| \geq 0$`</li> <li>`$|ab| = |a| \cdot |b|$`</li> <li>`$\pm a \leq |a|$`</li> <li>`$|a+b| \leq |a| + |b|$`: Dreiecksungleichung</li> <li>`$| |a| - |b| | \leq | a-b|$`</li> </ul> <p><strong>Beweis</strong>: 1, 2, 3 leichte Übung <strong>Beweis von 4.</strong>: Fall 1: <code>$a+b \geq 0$</code>. Dann <code>$|a+b| = a + b \leq |a| + |b|$</code> Fall 2: <code>$a+b \lt 0$</code>. Dann <code>$|a+b| = -(a+b) = (-a) + (-b) \leq |a| + |b|$</code> <strong>Beweis von 5.</strong>: <code>$c := |a| - |b|$</code>. Es ist <code>$|a| = |a - b + b| \leq |a - b | + |b| \Rightarrow |a| - |b| \leq |a - b|$</code>, also <code>$c \leq |a - b|$</code></p> <p>Analog: <code>$ -c = |b| - |a| \leq |b-a| = |a - b|$</code>. Es ist <code>$| |a| - |b| | = c \text{ oder } = -c$</code>.</p> <h3>Intervalle</h3> <p>Seien <code>$a, b \in \mathbb{R} \land a \lt b$</code>.</p> <p><code>$(a,b) := \{x \in \mathbb{R} a \lt x \lt b\}$</code>: offenes Intervall <code>$[a,b] := \{x \in \mathbb{R} a \leq x \leq b\}$</code>: geschlossenes Intervall <code>$(a,b] := \{x \in \mathbb{R} a \lt x \leq b\}$</code>: halboffenes Intervall <code>$[a,\infty) := \{x \in \mathbb{R} a \leq x \}$</code>. <code>$(a,\infty) := \{x \in \mathbb{R} a \lt x \}$</code>. <code>$(-\infty,a]:= \{x \in \mathbb{R} x \leq a \}$</code>. <code>$(-\infty,\infty):= \mathbb{R}$</code>. <code>$[a,a]:= \{a\}$</code>: entartetes Intervall</p> Create LaTeX timetable //martin-thoma.com/create-latex-timetable/ Tue, 18 Oct 2011 16:10:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/create-latex-timetable <p>LaTeX is a quite cool document markup language and document preparation system. You can easily create mathematical formulas.</p> <p>Today I’ve created a LaTeX timetable. Well, to be honest I have only used the timetable package from Pascal Gwosdek found on <a href="http://www.planetk.de/index.php/Stundenplan">planetk.de</a>.</p> <p>Here is the LaTeX-Code:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>\documentclass[a4paper,10pt]{report} % Definitions \usepackage{lscape} \usepackage[height=25cm]{geometry} \usepackage{timetable} \begin{document} \thispagestyle{empty} \begin{landscape} \noindent\printheading{Stundenplan von Martin Thoma - 1. Semester} % Define the layout of your time tables \setslotsize{2.8cm}{0.3cm} \setslotcount {5} {40} \settopheight{3} \settextframe{0.8mm} % Retro \setframetype[t]{1} \seteventcornerradius{0pt} % Print timestamps into event blocks %\setprinttimestamps{2} % Define event types \defineevent{lecture}{0.0} {0.28}{1.0} {1.0}{1.0}{1.0} \defineevent{exercise-course} {1.0} {0.4} {0.2} {1.0}{1.0}{1.0} \defineevent{tutorial} {0.6} {0.8} {1.0} {1.0}{1.0}{1.0} \defineevent{langcourse} {1.0} {0.4} {0.2} {1.0}{1.0}{1.0} \defineevent{work} {0.21}{0.5} {0.16}{1.0}{1.0}{1.0} % Start the time table \begin{timetable} \hours{8}{15}{1} \germandays{1} \event 1 {0945} {1115} {Betriebssysteme} {Bellosa} {10.23 Nusselt} {lecture} \event 1 {1130} {1300} {Wahrscheinlichkeits-theorie} {Hug} {11.40 Tulla HS} {lecture} \event 1 {1400} {1530} {Programmieren} {Pretschner} {50.35 HS a. F.} {lecture} \event 1 {1545} {1715} {LinAlg und Ana} {Leuzinger} {30.46 Neue Chemie} {exercise-course} \event 2 {0800} {0930} {Analysis I} {Schmoeger} {30.46 Neue Chemie} {lecture} \event 2 {0945} {1115} {Betriebssysteme} {Bellosa} {20.40 HS 37} {exercise-course} \event 2 {1130} {1300} {Theoretische Grundlagen der Informatik} {Wagner} {30.21 Gerthsen} {lecture} \event 3 {0800} {0930} {LinAlg und Analytische Geometrie I} {Leuzinger} {10.21 Daimler} {lecture} \event 3 {1400} {1530} {Grundbegriffe der Informatik} {Schultz} {50.35 HS a. F.} {lecture} \event 4 {0800} {0930} {Analysis I} {Schmoeger} {30.46 Neue Chemie} {lecture} \event 4 {1130} {1300} {Theoretische Grundlagen der Informatik} {Wagner} {30.21 Gerthsen} {lecture} \event 5 {0800} {0930} {LinAlg und Analytische Geometrie I} {Leuzinger} {11.40 Tulla HS} {lecture} \event 5 {0945} {1115} {Grundbegriffe der Informatik} {Schultz} {50.35 HS a. F.} {exercise-course} \event 5 {1545} {1715} {Analysis I} {Schmoeger} {10.21 Benz} {exercise-course} \end{timetable} \end{landscape} \end{document} </pre></div> </div> </div> <p>Here is the <a href="../images/2011/10/timetable.sty">timetable</a> and the <a href="../images/2011/10/example.tex">example timtable in LaTeX</a>. If you have a Linux machine, you can create the timetable with this command: <code>bash pdflatex example.tex -output-format=pdf </code></p> Einführung in die Stochastik //martin-thoma.com/einfuehrung-in-die-stochastik/ Mon, 17 Oct 2011 21:19:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/einfuehrung-in-die-stochastik <p>In diesem Artikel werde ich ein paar einfache Definitionen, die für die Stochastik wichtig sind, einführen.</p> <h2>Basisdefinitionen bei Zufallsexperimenten</h2> <p><strong>Was ist ein ideales Zufallsexperiment?</strong> Ein ideales <a href="http://de.wikipedia.org/wiki/Zufallsexperiment">Zufallsexperiment</a> sollte</p> <ul> <li>gut beschrieben,</li> <li>wiederholbar und</li> <li>mit mehreren m&ouml;glichen Ausg&auml;ngen (also zuf&auml;llig),</li> </ul> <p>sein. Die Zufallsgröße, wie beispielsweise die erwürfelte Zahl, nennt man <a href="http://de.wikipedia.org/wiki/Zufallsvariable">Zufallsvariable</a>. Es gibt auch noch die <a href="http://de.wikipedia.org/wiki/Statistische_Variable">Statistische Variable</a>. Wo der Unterschied ist, kann ich nicht sagen. Allerdings habe ich auf Wikipedia eine <a href="http://de.wikipedia.org/wiki/Diskussion:Statistische_Variable#Abgrenzung_Zufallsvariable_und_Statistische_Variable">Diskussion</a> geöffnet und hoffe auf baldige Klärung.</p> <p><strong>Was sind Merkmale?</strong> Merkmale sind die Ausgänge eines Zufallsexperiments. Sie können folgendermaßen gegliedert werden:</p> <ul> <li>quantitativ <small>(Die Zufallsgr&ouml;&szlig;e(n) haben nat&uuml;rlicherweise eine Ordnung)</small> <ul> <li>stetig <small>(Es k&ouml;nnen in einem Intervall beliebige Werte angenommen werden, z.B. die Gr&ouml;&szlig;e eines Menschen.)</small></li> <li>diskret <small>(Es k&ouml;nnen nur bestimmte Gr&ouml;&szlig;en angenommen werden, z.B. die Gr&ouml;&szlig;e eines Menschen in ganzen Zentimetern.)</small></li> </ul> </li> <li>qualitativ <small>(Es gibt keine nat&uuml;rliche Ordnung.)</small> <ul> <li>ordinal <small>(Es geht um Zahlengr&ouml;&szlig;en, z.B. Noten.)</small></li> <li>nominal <small>(Etwas v&ouml;llig anderes, z.B. Geschlecht.)</small></li> </ul> </li> </ul> <p><strong>Urliste / Stichprobe</strong> vom Umfang n: <code>$x := (x_1, x_2, ..., x_n)$</code> <code>$H_x (a_j) := \text{Anzahl der Stichprobenelemente in x, die gleich} a_j \text{sind}$</code> <code>$H_x (a_j)$</code> : <strong>Absolute Häufigkeit</strong> <code>$h_x(a_j) := \frac{H_x (a_j)}{n}$</code> : <strong>Relative Häufigkeit</strong> <strong>Empirische Verteilungsfunktion</strong> <code>$t \mapsto \underbrace{F_x(t)}_{\text{empirische Verteilungsfunktion}} := \sum \limits_{j: a_j \le t} {h_x (a_j)}, t \in \mathbb{R}$</code> Eine alternative Definition der <a href="http://de.wikipedia.org/wiki/Empirische_Verteilungsfunktion">empirischen Verteilungsfunktion</a> ist <code>$F_x(t) := \frac{1}{n} \sum \limits_{i=1}^n 1 \{ x_i \le t \}$</code></p> <p><strong>Arithmetisches Mittel</strong> (“Durchschnitt”): <code>$\overline x = \frac{1}{n} \sum \limits_{i=1}^n x_i = \frac{x_1 + ... + x_n}{n}$</code> Welcher Wert liegt in der Mitte?</p> <p><strong>Stichproben-Varianz</strong>: <code>$s_x^2 := \frac{1}{n-1} \sum \limits_{i = 1}^n (x_i - \overline x)^2$</code> <strong>Stichproben-Standardabweichung</strong>: <code>$s_x := + \sqrt{s_x^2}$</code> Wie stark weichen die Werte von einander ab?</p> <p><strong>Stichproben-Variationskoeffizient</strong>: <code>$v_x := \frac{s_x}{\overline x}$</code> Wie groß ist die Schwankung relativ zum Durchschnitt?</p> <p><strong>Stichproben-Median / Zentralwert</strong>: Würde mal alle Werte einer Stichprobe sortieren, sollte der Median der Wert in der Mitte sein. Das ist <em>nicht</em> der Durchschnitt! <code>$\tilde x := \begin{cases} x_{\frac{n+1}{2}}, &amp; \mbox{wenn } n \mbox{ ungerade} \\ \frac{1}{2} (x_\frac{n}{2} + x_{\frac{n}{2} + 1}), &amp; \mbox{wenn } n \mbox{ gerade} \end{cases}$</code></p> <p><strong>Quantil</strong>: Das Quantil unterteilt die Verteilung der Werte der Zufallsvariablen in zwei Bereiche: Links vom <code>$\alpha$</code>-Quantil liegen <code>$100 \cdot p$</code> Prozent aller Beobachtungswerte bzw. <code>$100 \cdot p$</code> Prozent der Gesamtzahl der Zufallswerte. Rechts davon liegen <code>$100 \cdot (1-p)$</code> Prozent aller Beobachtungswerte bzw. <code>$100 \cdot (1-p)$</code> Prozent der Gesamtzahl der Zufallswerte.</p> <p>Das Quartil ist das 0,25-Quantil.</p> <p><code>$\alpha$</code>-getrimmtes Stichprobenmittel: <code>$\overline x_\alpha := \frac{1}{n-2k} \cdot (x_{n+1} + ... + x_{n-k})$</code> Spezialfall: <code>$\overline x = \overline x_0$</code></p> <p>Quartilsabstand: <code>$\tilde x_{0,75} - \tilde x_{0,25}$</code> Spannweite: <code>$x_n - x_1$</code></p> <h2>Visualisierungen</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/boxplot-300x119.png"><img src="../images/2011/10/boxplot-300x119.png" alt="Boxplot" width="" height="" class="size-medium wp-image-5981" /></a><p class="wp-caption-text"><a href="http://de.wikipedia.org/wiki/Boxplot">Boxplot</a></p></div> <p>Weitere Visualisierungsmöglichkeiten:</p> <ul> <li>Punktwolke</li> <li><a href="http://de.wikipedia.org/wiki/Streudiagramm">Streudiagramm</a></li> </ul> <h2>Ann&auml;herungen</h2> <p>Durch eine <a href="http://de.wikipedia.org/wiki/Regressionsanalyse">Regressionsanalyse</a> kann man ein Regressionsmodell erstellen. Es legt den Typ einer Regressionsfunktion fest. Eine Regressionsfunktion kann z.B. die <a href="http://de.wikipedia.org/wiki/Regressionsfunktion">Methode der kleinsten Quadrate</a> sein: <code>$\sum \limits_{j=1}^{n}\overbrace{(\underbrace{y_i -a -b \cdot x_j}_{\text{Residuum}})^2}^{ \begin{array}{l} \text{Damit sich negative positive}\\ \text{Abweichungen nicht gegenseitig}\\ \text{aufheben} \end{array} }$</code></p> <h3>Geradenparameter errechnen</h3> <p>Tja, hier hat er die Folien viel zu schnell durchgeschaltet … ich habe nur folgendes:</p> <p>Regressionsgerade: <code>$y = a^* + b^* \cdot x$</code> (eindeutig bestimmbar) <code>$b^* = \frac{\sum \limits_{j=1}^n (x_j - \overline x) (y_j - \overline y)} {\sum \limits_{j = 1}^n (x_j - \overline x)^2}$</code></p> <p>und <code>$a^* = \overline y - b^* \cdot \overline x$</code></p> <p>mit <code>$r_{xy} = \frac{\frac{1}{n-1} \sum \limits_{j=1}^n (x_i - \overline x)(y_j - \overline y)} {b_x \cdot b_y}$</code> (Korrelationskoeffizient der Daten)</p> <p>gilt <code>$b^* = r_{xy} \cdot \frac{s_y}{s_x}$</code></p> <p>Irgendwas war noch mit der <a href="http://de.wikipedia.org/wiki/Cauchy-Schwarzsche_Ungleichung">Cauchy-Schwarz Ungleichung</a>.</p> <p>Falls jemand Anmerkungen hat, mehr mitgeschrieben hat oder einfach Fragen aufkommen: Postet doch einen Kommentar!</p> Password Changing Services //martin-thoma.com/password-chaning-services/ Mon, 17 Oct 2011 08:10:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/password-chaning-services <p>Today I’ve changed my PayPal password, because I thought it was time to do so. Now I know that the password changing service of PayPal can be improved quite a lot. I had to type the password about twelve times! This is the reason why I thought it was time to create some principles for good password chaning services:</p> <p><strong>User authentification</strong>: It is important that only the user can change the password. You have to force the user to type in his old password again. This should be done as a first step in the authentification. Nothing is more frustrating than beeing forced to type in your old password again and again as your new password wasn’t valid. You could check if he typed in his old password less than a minute ago.</p> <p><strong>Eliminate typos</strong>: Like every good service, PayPal wants you to type the password and the verification. It would be good, if two symbols were added to the textbox. One for the activiation of <a href="http://en.wikipedia.org/wiki/Caps_lock">caps lock</a> and one for <a href="http://en.wikipedia.org/wiki/Num_lock">num lock</a>. I think this has to be done by the browser.</p> <p><strong>Clientside validation</strong>: The first time, I used a password which was considered as weak. A JavaScript informed me that it was weak, but I could submit the form. The form should be validated on the client. If it is not valid, don’t let him submit the form. (The password has to be validated also on the server, of course.)</p> <p><strong>Allow all characters</strong>: I was very negatively surprised as I was informed that PayPal doesn’t allow “non-printable characters” like spaces. They informed me after I submitted, of course. It does make sense to warn the user if he uses special characters which might be difficult to type on other systems, like german umlauts (äöüÄÖÜß). But why the hell do they force me to use underscores instead of spaces? Do they print my password? Do they want that I print my password?</p> <p><strong>Allow “weak” passwords</strong>: You should not allow weak passwords, of course. But you should have a good definition of weak. Less than 6 characters is weak. I wanted to use a 26-character password with upper- and lower case letters, spaces and one special character. This was considered as weak. If you read <a href="../md5-cracking/" title="MD5 cracking">my post about MD5 cracking</a> you have probably noticed, that it is much harder to crack a 26-character password with only lower case letters than a 8 character password with lower case, upper case and numbers. About <code>$10^{22}$</code> times as much passwords are possible with 26 characters and 26 letters than with a character-space of 62 elements but only 8 places (see <a href="http://www.wolframalpha.com/input/?i=26^26%2F%2826*2%2B10%29^8">Wolfram|Alpha</a>). You can easily build a password if you use a sentence, not a word. This will be long and will quite possibly only have lower case letters, spaces and one upper case letter, but it is possible to remember it.</p> <figure class="wp-caption aligncenter"> <img src="http://imgs.xkcd.com/comics/password_strength.png" alt="Password Strength" /> <figcaption>Password Strength</figcaption> </figure> <p><strong>Allow long passwords</strong>: As the passwords should not be stored as plaintext, but hashed it doesn’t really matter how long they are. If you use MD5, it will always take 32 characters. Why should you limit a user to only 20 characters (like PayPal does)? If the 26 character password is easier to remember, why do you want to restrict him to a shorter password which is easier to crack?</p> <p>I made the same annoying experiences with the password of my students account for university. They forced me to use a short password with a lower case and upper case letters, digits and special characters.</p> <p>Do you have some more suggestions for good passwords? Which websites have a very good password changing service?</p> MD5 cracking //martin-thoma.com/md5-cracking/ Mon, 17 Oct 2011 07:36:15 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/md5-cracking <p>MD5 is a cryptographic hash function. This means, you can give the MD5 algorithm a string and it will return another 32-character long alphanumeric string. The returned string looks quite random, but it isn’t. If you use the same input, you always get the same 32 character output.</p> <p>What is it good for?</p> <p>Well, imagine you had a web application. Now an attacker found a security whole and can read the password-column in the database. If it was plain text, he could use the passwords to log into the users accounts. As it is hashed and the hash function can’t be simply reverted. So the attacker can’t take any advantage of the passwords he just read.</p> <p>It is much more realistic that the attacker can read the whole database. So he can access sensitive user data. As it is very likely that you have some e-mail adresses in there, he could quite probably log into the e-mail accounts of the users with the same password. If the password is hashed, it’s not that simple. He has to try to crack the MD5 hashed passwords.</p> <p>I’ll describe and test in the following how easy this is and how it could be done.</p> <h2 id="tested-hashes">Tested Hashes</h2> <p>MD5 is a widely used cryptographic hash function. I wanted to know how easy it is to crack them, so I tested it. I used those passwords:</p> <ul> <li>"computer": df53ca268240ca76670c8566ee54568a</li> <li>"establishment": f469410e5ec7594a9c41603e06ccf6a3</li> <li>"My Birthday": ce9dbd008dac54422b90b3f82f58dd40</li> <li>"I'm born in 1990.": 834649b6298642a7576b10c6705842d8</li> <li>"r4Nd0m9": cc11c3de28e4425eff27b2fb5f216903</li> </ul> <h2>Online Crackers</h2> <p>If you search for “md5 cracker” you find <a href="http://md5cracker.org/" rel="nofollow">some md5 crackers</a>. This website could crack <em>computer</em>, <em>establishment</em> and <em>My Birthday</em>. The other two hashes weren’t cracked.</p> <h2>John the Ripper</h2> <p>Ubuntu-Users can easily install John the Ripper (sudo apt-get install john) and use it for cracking hashes. To do so, the have to create a file in their working directory (let’s call it md5.txt) and execute the following command:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">john --format<span class="o">=</span>raw-MD5 md5.txt</code></pre></div> <p>Here is the time, john needed to crack the hashes:</p> <ul> <li>"computer": 0.521 seconds</li> <li>"establishment": after 1 h it wasn't cracked</li> <li>"My Birthday": after 5 min it wasn't cracked</li> <li>"I'm born in 1990.": after 5 min it wasn't cracked</li> <li>"r4Nd0m9": after 38 min it wasn't cracked</li> </ul> <p>Okay, these results aren’t good. But you can also use a wordlist (e.g. the 15 MB list from http://www.bright-shadows.net/download/downloads.php) and the command john –wordlist:tbswordlist1.txt –format=raw-MD5 md5.txt</p> <ul> <li>"computer": df53ca268240ca76670c8566ee54568a</li> <li>"establishment": 0.568 seconds</li> <li>"My Birthday": not cracked</li> <li>"I'm born in 1990.": not cracked</li> <li>"r4Nd0m9": not cracked</li> </ul> Challenge Websites //martin-thoma.com/challenge-websites/ Tue, 11 Oct 2011 21:57:21 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/challenge-websites <p>Challenge websites are websites which offer many tasks to solve and a ranking system. If you solve the challenges, you get points and your rank increases. You don’t get anything else. No money, no price. Only the knowledge and the ranking. Which is enough in my opinion. It might sound strange to others, but its fun to try to find the error in an application or to try to get better than others.</p> <p>The topics could be anything, but most of the time you should exploit a security whole.</p> <p>All Challenge websites I know use categories to organize their challenges. I’ll describe some of them later.</p> <h2>Why should challenge websites be more famous?</h2> <p>Some people think its exciting to get to know the internals of a system. Questions like “What will happen if I take the absolute value of -2,147,483,648?” come automatically to their mind. <small>If you are not one of those guys, you might ask yourself “Why -2147483648? Why not -1234?”. Well, the simple answer is that in almost every programming language integers have 32 bytes. This means, you can store 2^32 values in this variable. As you have negative numbers, only 2^31 for each side. As you have 0, for one side one less. The range of an integer is in most languages -2^31 to +(2^31 -1). So if you take the absolute value of -2^31, you’re out of that range.</small> It is much more interesting to get to know what could possibly go wrong in other systems and to show others your punditry than setting up an isolated system and trying to get unexpected results. If you don’t know about challenge websites it is quite likely that you will try your knowledge on productive systems. This might result in a real damage.</p> <p>Another reason why challenge websites should get more famous is the moral compass. Even very young children can get an awfully amout of knowledge in computers. They might be able to hack others, but they don’t have a feeling for whats wrong and right. If they try their knowledge in on a challenge website, they get a community they can talk to. I guess the administrators will not be happy if they exploit their systems, but if they tell them how to fix it I guess they would not go to the police. (As it is very likely that the attacker didn’t really cause any damage like the loss of personal information or shutting down a system for which customers paid for, I think it is very unlikely that they will got to police.). I think it’s very likely that they will give the credits for the patch / bug on their site. hacker.org does so, for example.</p> <p>I could also imagine that software companies could be interested in such websites. Wouldn’t it be a great idea to post programming challenges and to contact the people who rank high?</p> <h2>What are common categories?</h2> <h3>JavaScript</h3> <p>JavaScript password protections are not secure. They are very easy to exploit and the website owner can be sure, that he will not open a real security leak when he creates such a challenge.</p> <p>Some common tasks include:</p> <ul> <li>Looking into the source code of the webpage</li> <li>Deactivating JavaScript because you are redirected</li> <li>Understanding JavaScript</li> </ul> <h3>Exploit</h3> <p>Many websites have server side bugs or vulnerabilities. So you can create challenges for “hackers” to find and exploit those to get to a hidden page. These exploits could be:</p> <ul> <li><a title="http://en.wikipedia.org/wiki/SQL_injection" href="http://en.wikipedia.org/wiki/SQL_injection">SQL injections</a></li> <li><a title="Cross-site scripting" href="http://en.wikipedia.org/wiki/Cross-site_scripting">XSS</a></li> <li>Missing password protection</li> <li><a title="Code injection" href="http://en.wikipedia.org/wiki/Code_injection">Code injection</a></li> <li>Possible rights escalation</li> </ul> <h3>Cryptography</h3> <p><a title="http://en.wikipedia.org/wiki/Cryptography" href="http://en.wikipedia.org/wiki/Cryptography">Cryptography</a> is the practice and study of techniques for secure communication in the presence of third parties. This means you know that others will read your messages, but this doesn’t mean they have to get to know what it means. They will only see rubbish and hopefully they don’t know how to translate it into a meaningful sentence.</p> <p>As cryptography is older than computers you can find very many cryptographical challenges. One of the most common ones is the <a title="Caesar cipher" href="http://en.wikipedia.org/wiki/Caesar_cipher">Caesar cipher</a>.</p> <p>Most ciphers are in at least one of the following categories:</p> <ul> <li>Classical Ciphers</li> <li>Substitution Ciphers</li> <li>Transposition Ciphers</li> <li>Block Ciphers</li> <li>Symmetrical Ciphers</li> <li>Asymmetrical Ciphers</li> </ul> <h3>Steganography</h3> <p>Steganography is the art of hiding data. In the case of cryptography, your opponent knows that he has the information. In case of steganography he might think that he has only a nice picture. Did you ever use invisible ink as a child? Congratulations, you have already applied steganography!</p> <p>Some common steganographic challenges are:</p> <ul> <li>Looking at the source code of a webpage</li> <li>Looking very exactly at a high resolution image</li> <li>Examining a .gif with multiple layers / a video</li> <li>Playing a sound really slow / fast</li> <li>Playing with the bits of an image</li> </ul> <h3>CrackIts</h3> <p>CrackIts are challenges where you have to change a binary to get the results. Cracks are quite common. Perhaps you know that some illegal versions a very expesive software which can be found online don’t need the registration code. They were cracked.</p> <h3>Flash / Java Applets</h3> <p>It is basically always decompiling and understanding the crappy output. As a reallife-application you could imagine an online game where you want to get into the highscore. Decompile it, look at the place where it gets submitted and submit your wished high score.</p> <h3>Programming</h3> <p>Programming challenges have a time component. You need to solve a specific instance of a problem in, well, lets say three seconds. Enough time for a computer to connect to the webpage, download the problem, solve it and upload the solution. Most of the time by far not enough to solve it by hand.</p> <h3>Logic, Math and Science</h3> <p>A classical logic challenge is the <a title="Sphinx riddle" href="http://en.wikipedia.org/wiki/Sphinx%27_riddle#The_Riddle_of_the_Sphinx">riddle of the Sphinx</a>. Another one is <a title="Einstein's Riddle" href="http://en.wikipedia.org/wiki/Zebra_Puzzle">Einstein’s riddle</a>.</p> <p>I guess you can imagine what a math challenge is? 1 + 1 = x, solve to x would be one. The <a title="Impossible Puzzle" href="http://en.wikipedia.org/wiki/Impossible_Puzzle">Impossible Puzzle</a> would be another one.</p> <p>The science challenges are like the homework I had to do in school. Some are very difficult, others are quite easy. But the kind of quesions which were very simmilar to the questions in school.</p> <h3>Information Gathering</h3> <p>Almost every challenge could also be in the “Information Gathering” category. Who doesn’t try Google first? (Except if the answer is obvious, of course.)</p> <p>Basic tasks are to get to know something about the owner of a specific website or about the content of a website a few years ago.</p> <h2>Some examples</h2> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/bright-shadows-300x138.png"><img src="../images/2011/10/bright-shadows-300x138.png" alt="Bright Shadows - The Back Sheep" width="" height="" class="size-medium wp-image-5301" /></a><p class="wp-caption-text"><a href="http://www.bright-shadows.net/">www.bright-shadows.net</a> - The Back Sheep</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/hacker.org_-300x175.png"><img src="../images/2011/10/hacker.org_-300x175.png" alt="hacker.org" width="" height="" class="size-medium wp-image-5311" /></a><p class="wp-caption-text"><a href="http://www.hacker.org/">hacker.org</a></p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/wechall-300x140.png"><img src="../images/2011/10/wechall-300x140.png" alt="WeChall" width="" height="" class="size-medium wp-image-5321" /></a><p class="wp-caption-text"><a href="http://www.wechall.net/">WeChall</a></p></div> <p><a href="http://projecteuler.net/">ProjectEuler</a> - for people who are interested in math challenges: <img src="http://projecteuler.net/profile/moose.png" /></p> When Geeks get Parents //martin-thoma.com/when-geeks-get-parents/ Mon, 10 Oct 2011 07:54:07 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/when-geeks-get-parents <p>It’s so funny what happens when Geeks get parents.</p> <p>This is what happens if your dad is a designer: <a href="../images/2011/10/baby-8.jpg"><img src="../images/2011/10/baby-8.jpg" alt="Baby" title="Baby" width="519" height="367" class="aligncenter size-full wp-image-5151" /></a></p> <p><a href="../images/2011/10/baby-9.jpg"><img src="../images/2011/10/baby-9.jpg" alt="Baby 9" title="Baby 9" width="520" height="367" class="aligncenter size-full wp-image-5161" /></a></p> <div style="width: 530px" class="wp-caption aligncenter"><a href="../images/2011/10/baby-batman.jpg"><img src="../images/2011/10/baby-batman.jpg" alt="Baby Batman" width="" height="" class="size-full wp-image-5171" /></a><p class="wp-caption-text">Baby Batman</p></div> <div style="width: 529px" class="wp-caption aligncenter"><a href="../images/2011/10/baby-hogan.jpg"><img src="../images/2011/10/baby-hogan.jpg" alt="Baby Hulk Hogan" width="" height="" class="size-full wp-image-5181" /></a><p class="wp-caption-text">Baby <a href="http://en.wikipedia.org/wiki/Terry_Gene_Bollea">Hulk Hogan</a></p></div> <div style="width: 531px" class="wp-caption aligncenter"><a href="../images/2011/10/baby-ogre.jpg"><img src="../images/2011/10/baby-ogre.jpg" alt="Baby Ogre" width="" height="" class="size-full wp-image-5191" /></a><p class="wp-caption-text">Baby Ogre</p></div> <div style="width: 531px" class="wp-caption aligncenter"><a href="../images/2011/10/baby-soldier.jpg"><img src="../images/2011/10/baby-soldier.jpg" alt="Baby Soldier" width="" height="" class="size-full wp-image-5201" /></a><p class="wp-caption-text">Baby Soldier</p></div> <div style="width: 530px" class="wp-caption aligncenter"><a href="../images/2011/10/baby-vampire.jpg"><img src="../images/2011/10/baby-vampire.jpg" alt="Baby Vampire" width="" height="" class="size-full wp-image-5211" /></a><p class="wp-caption-text">Baby Vampire</p></div> <p>The Original (or at least the highest resolution I found) is <a href="http://sneezl.com/wp-content/uploads/2008/04/graphic-designer-baby.pdf">here as PDF</a>.</p> <p>Giving your child some funny T-shirts is also quite common:</p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/geek-baby-no.jpg"><img src="../images/2011/10/geek-baby-no.jpg" alt="Baby Geek: No!" width="" height="" class="size-full wp-image-5251" /></a><p class="wp-caption-text">Baby Geek: No! (found on <a href="http://www.zazzle.de/lieblingswort_ist_no_chemie_aussenseiter_baby_ones_tshirt-235215790093704490">zazzle</a>)</p></div> <div style="width: 335px" class="wp-caption aligncenter"><a href="../images/2011/10/geek-baby-rpg.jpg"><img src="../images/2011/10/geek-baby-rpg.jpg" alt="RPG Geek Baby" width="" height="" class="size-full" /></a><p class="wp-caption-text">It seems like someone liked RPGs <a href="http://postmortemstudios.wordpress.com/2011/09/12/sowygo1-a-geek-is-born/">here</a> ☺</p></div> <p>A friend of mine just shared this photo:</p> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2011/10/geek-twins.jpg"><img src="../images/2011/10/geek-twins.jpg" alt="Twins: Copy and Paste" width="" height="" class="size-full" /></a><p class="wp-caption-text">Twins: Copy and Paste. Thanks to Ren&eacute; for sharing</p></div> <p>Do you have more images or perhaps stories of geeky parents? Please let me know in a comment!</p> Game: QWERTY Warriors 2 //martin-thoma.com/game-qwerty-warriors-2/ Sat, 08 Oct 2011 21:44:24 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/game-qwerty-warriors-2 <div style="width: 559px" class="wp-caption aligncenter"><a href="../images/2011/09/QWERTY-Warriors-2.png"><img src="../images/2011/09/QWERTY-Warriors-2.png" alt="QWERTY Warriors 2" width="" height="" class="size-full wp-image-4971" /></a><p class="wp-caption-text">QWERTY Warriors 2</p></div> <p><b>Go to the Game</b>: <a href="http://www.kongregate.com/games/Weasel/qwerty-warriors-2">QWERTY Warriors 2 on Kongregate</a> <b>Task</b>: Survive as long as possible. <b>How to play</b>: You have to type the enemy-words as fast as possible. Your figure will automatically shoot at them when you type. <b>My Record</b>: 118,486 (Final Score, see below)</p> <div style="width: 559px" class="wp-caption aligncenter"><a href="../images/2011/10/QWERTY-Warriors-2-Score.png"><img src="../images/2011/10/QWERTY-Warriors-2-Score.png" alt="QWERTY Warriors 2: Score" width="" height="" class="size-full wp-image-4981" /></a><p class="wp-caption-text">QWERTY Warriors 2: Score</p></div> Order categories in WordPress //martin-thoma.com/order-categories-in-wordpress/ Sat, 08 Oct 2011 14:18:19 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/order-categories-in-wordpress <p>Today, I’ve introduced a new category: My bits and bytes. I wanted to write something about my <a href="../kitchen-renovation-part-1/">kitchen renovation</a>. Additionally, I thing I will write from time to time about other topics than computer related ones.</p> <p>As I looked at my categories, I saw that they were ordered lexicographically. But I called my Blog “Code, the Web and Cyberculture”, not “Code, Cyberculture and the Web”. So I had to change it.</p> <p>Lucily, a plugin called <a href="http://wordpress.org/extend/plugins/order-categories/">Category Orders</a> exists. It works fine with the latest WordPress (3.2.1):</p> <div style="width: 266px" class="wp-caption aligncenter"><a href="../images/2011/10/WordPress-Plugin-Category-Orders-256x300.png"><img src="../images/2011/10/WordPress-Plugin-Category-Orders-256x300.png" alt="WordPress Plugin: Category Orders" width="" height="" class="size-medium wp-image-4911" /></a><p class="wp-caption-text">WordPress Plugin: Category Orders</p></div> Kitchen renovation - Part 1 //martin-thoma.com/kitchen-renovation-part-1/ Sat, 08 Oct 2011 12:01:40 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/kitchen-renovation-part-1 <p>Most of you might know that I am currently a student. Living near the University is quite important for me as I hate traveling long. In the central part of <a href="http://en.wikipedia.org/wiki/Karlsruhe">Karlsruhe</a>, the city I study in, most houses are very old. The house I live in was built around 1900 and modernized from time to time. A heater and electricity were added, for example.</p> <p>The flat is shared by students. My hirer told me that he will pay all cost of materials if I wanted to improve something. As a new leaser came and we had no washing machine we thought it was time to renovate the kitchen.</p> <h2>The old kitchen</h2> <h3>Why did I renovate?</h3> <ul> <li>We needed more space for a new washing machine.</li> <li>The old countertop was ugly, molded and had a water damage.</li> <li>The tap was loose.</li> <li>The tube for hot water was loose.</li> </ul> <h3>Some photos</h3> <div style="width: 610px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-before-countertop.jpg"><img src="../images/2011/10/kitchen-before-countertop.jpg" alt="Old countertop of our kitchen" width="" height="" class="size-full wp-image-4281" /></a><p class="wp-caption-text">Old countertop of our kitchen</p></div> <div style="width: 385px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-before-countertop-old.jpg"><img src="../images/2011/10/kitchen-before-countertop-old.jpg" alt="The old countertop" width="" height="" class="size-full wp-image-4301" /></a><p class="wp-caption-text">The old countertop</p></div> <div style="width: 610px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-before-countertop-old-top.jpg"><img src="../images/2011/10/kitchen-before-countertop-old-top.jpg" alt="Top of the old countertop" width="" height="" class="size-full wp-image-4331" /></a><p class="wp-caption-text">Top of the old countertop</p></div> <h2>Plans</h2> <div style="width: 684px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-before-plan.png"><img src="../images/2011/10/kitchen-before-plan.png" alt="Kitchen before renovation" width="" height="" class="size-full wp-image-4551" /></a><p class="wp-caption-text">Kitchen before renovation</p></div> <div style="width: 685px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-after-plan.png"><img src="../images/2011/10/kitchen-after-plan.png" alt="Kitchen after renovation" width="" height="" class="size-full wp-image-4561" /></a><p class="wp-caption-text">Kitchen after renovation</p></div> <h2>The renovation</h2> <h3>Tools</h3> <p>I needed quite a lot of tools. I had to buy most of them when I saw that I couldn’t continue without them:</p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/tool-drilling-machine.jpg"><img src="../images/2011/10/tool-drilling-machine.jpg" alt="Drilling machine" width="" height="" class="size-full wp-image-4571" /></a><p class="wp-caption-text">Drilling machine</p></div> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/tool-plumber-wrench.jpg"><img src="../images/2011/10/tool-plumber-wrench.jpg" alt="Plumber wrench" width="" height="" class="size-full wp-image-4581" /></a><p class="wp-caption-text">Plumber wrench</p></div> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/tool-screwdriver.jpg"><img src="../images/2011/10/tool-screwdriver.jpg" alt="Screwdrivers" width="" height="" class="size-full wp-image-4591" /></a><p class="wp-caption-text">Screwdrivers</p></div> <div style="width: 510px" class="wp-caption aligncenter"><a href="../images/2011/10/tool-silicone-cartridge.jpg"><img src="../images/2011/10/tool-silicone-cartridge.jpg" alt="Silicone cartridge" width="" height="" class="size-full wp-image-4611" /></a><p class="wp-caption-text">Silicone cartridge</p></div> <div style="width: 610px" class="wp-caption aligncenter"><a href="../images/2011/10/tool-spirit-level.jpg"><img src="../images/2011/10/tool-spirit-level.jpg" alt="Spirit level" width="" height="" class="size-full wp-image-4621" /></a><p class="wp-caption-text">Spirit level</p></div> <div style="width: 300px" class="wp-caption aligncenter"><a href="../images/2011/10/tool-wrench.jpg"><img src="../images/2011/10/tool-wrench.jpg" alt="Wrench" width="" height="" class="size-full wp-image-4631" /></a><p class="wp-caption-text">Wrench</p></div> <p>Additionally I needed a hammer to get the wall plugs into the wall, some different screws and wall plugs, pliers, some tubes and some <a href="http://en.wikipedia.org/wiki/O-ring">O-rings</a>.</p> <h3>Photos while working</h3> <div style="width: 206px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-crooked-wall2-196x300.jpg"><img src="../images/2011/10/kitchen-working-crooked-wall2-196x300.jpg" alt="Crooked wall" width="" height="" class="size-medium wp-image-4641 " /></a><p class="wp-caption-text">Crooked wall</p></div> <div style="width: 235px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-after-heating-pipe-225x300.jpg"><img src="../images/2011/10/kitchen-after-heating-pipe-225x300.jpg" alt="Heating pipes" width="" height="" class="size-medium wp-image-4671 " /></a><p class="wp-caption-text">Heating pipes</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-washing-machine-300x225.jpg"><img src="../images/2011/10/kitchen-working-washing-machine-300x225.jpg" alt="Washing machine" width="" height="" class="size-medium wp-image-4741" /></a><p class="wp-caption-text">To save some money and to be sure that it really fits, I waited with the renovation until the washing machine was delivered. After it was here I had to move it quite often to get the ledge at it&#039;s place.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-loose-tube-300x225.jpg"><img src="../images/2011/10/kitchen-working-loose-tube-300x225.jpg" alt="A loose tube was mounted to the wall" width="" height="" class="size-medium wp-image-4821" /></a><p class="wp-caption-text">As I removed the old countertop, I saw that a tube was loose. This had to be fixed. So I mounted it to the wall.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-ledge2-300x225.jpg"><img src="../images/2011/10/kitchen-working-ledge2-300x225.jpg" alt="Adding a working ledge" width="" height="" class="size-medium wp-image-4721" /></a><p class="wp-caption-text">Adding a working ledge is very important. It gives your countertop the needed stability and you can make sure that it&#039;s exactly horizontally. Therefore you should use a spirit level.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-connection-300x214.jpg"><img src="../images/2011/10/kitchen-working-connection-300x214.jpg" alt="Connect countertops" width="" height="" class="size-medium wp-image-4811" /></a><p class="wp-caption-text">You have to connect both countertops very good. If you don&#039;t do so, you will get water in there which will destroy the countertop over time. So we filled the space in between with wood glue and pressed them together with this screw construction.</p></div> <div style="width: 269px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-tab-259x300.jpg"><img src="../images/2011/10/kitchen-working-tab-259x300.jpg" alt="The tab was fixed to the countertop." width="" height="" class="size-medium wp-image-4831" /></a><p class="wp-caption-text">This little metal plate fixates the tap to the countertop. I put it for two days into vinegar to get rid of most of the rust, dirt and chalk. Before I did so, the whole plate was brown.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-angle-joints-300x225.jpg"><img src="../images/2011/10/kitchen-working-angle-joints-300x225.jpg" alt="Angle joints for crabbing the countertop to the wall" width="" height="" class="size-medium wp-image-4801" /></a><p class="wp-caption-text">Angle joints fix the countertop to the wall. I used 23 angle joints with 46 screws. Nothing will separate my countertop from the wall :D</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-working-silicone-leftovers-300x225.jpg"><img src="../images/2011/10/kitchen-working-silicone-leftovers-300x225.jpg" alt="Silicone leftovers" width="" height="" class="size-medium wp-image-4711" /></a><p class="wp-caption-text">Removing silicone leftovers is a pretty time intensive work. You can remove a lot with a knife, but if the underground is tender you have to use some chemicals.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-masked-countertop-300x225.jpg"><img src="../images/2011/10/kitchen-masked-countertop-300x225.jpg" alt="Masked countertop" width="" height="" class="size-medium wp-image-4701" /></a><p class="wp-caption-text">If you want to make a clean silicone clogging, you should mask the surrounding area.</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-after-baseboard-300x225.jpg"><img src="../images/2011/10/kitchen-after-baseboard-300x225.jpg" alt="Adding a baseboard" width="" height="" class="size-medium wp-image-4781" /></a><p class="wp-caption-text">Adding a baseboard was one of the last steps. This small piece of would should prevent water from touching the wallpaper. Moreover it looks nice ☺</p></div> <h2>The new kitchen</h2> <div style="width: 610px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-after.png"><img src="../images/2011/10/kitchen-after.png" alt="Kitchen after renovation" width="" height="" class="size-full wp-image-4651" /></a><p class="wp-caption-text">Kitchen after renovation</p></div> <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/10/kitchen-after-exact-work-300x225.jpg"><img src="../images/2011/10/kitchen-after-exact-work-300x225.jpg" alt="Exact work: It fitted only with a few milimeters left" width="" height="" class="size-medium wp-image-4771" /></a><p class="wp-caption-text">Exact work: It fitted only with a few milimeters left. Good that I added some space to make sure it will fit. If I made the plate exactly as big as it could have been according to my first plan, I would have been in trouble.</p></div> <h2>Conclusion</h2> <p>I am proud of the result. The new kitchen looks nice, the countertop is very exact horizontally, no water drips out. Some parts could have been done better (like the silicone clogging), but I guess most could not be much better.</p> <p>The next time I do something like this I will hopefully not have to go about ten times to the hardware store :-/ Now I have some more tools :D</p> 5 Web Technologies which should be used more often //martin-thoma.com/5-web-technologies-which-should-be-used-more-often/ Sat, 08 Oct 2011 06:21:25 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/5-web-technologies-which-should-be-used-more-often <div style="width: 110px" class="wp-caption alignright"><a href="../images/2011/10/RSS-Feeds.png"><img src="../images/2011/10/RSS-Feeds.png" alt="RSS-Feeds" width="" height="" class="size-full wp-image-4411" /></a><p class="wp-caption-text">RSS-Feeds</p></div> <h2 id="rss-feeds">RSS-Feeds</h2> <p>Everyone who wants to get informed about updates on websites has to use RSS Feeds. Every time any website you have in your Feed Reader makes an update, you can get instantly a little notice. Its a bit like e-mail, but you have the possibility to stop this service. You can’t get spam, as the Feed owner doesn’t get an identifier for you.</p> <div style="width: 110px" class="wp-caption alignright"><a href="../images/2011/10/OpenID.png"><img src="../images/2011/10/OpenID.png" alt="OpenID" width="" height="" class="size-full wp-image-4431" /></a><p class="wp-caption-text">OpenID</p></div> <h2 id="openid">OpenID</h2> <p>It is really annoying to register on every single page you use. The idea behind OpenID is having one account for registering on many domains. If you want to log-in in Blogger, you are sent to Google. You type in your username and password and Google sends you back to Blogger.</p> <p>Here is another explanation:</p> <iframe title="YouTube video player" class="youtube-player" type="text/html" width="512" height="414" src="http://www.youtube.com/embed/xcmY8Pk-qEk" frameborder="0" allowfullscreen=""></iframe> <p>The process seems to be too complex for many users, so Google developed the <a href="http://code.google.com/intl/de-DE/apis/identitytoolkit/index.html">Google Identity Toolkit</a> (GIT). The technique is really nice, but I don’t like the idea that I have to force my users to use Google (or a service of them). Though I use Google for almost everything.</p> <h2 id="ajax">Ajax</h2> <p><a href="http://en.wikipedia.org/wiki/Ajax_(programming)" rel="nofollow">Ajax</a> is a programming style. If you like to view another page or get some information which isn’t already loaded, you don’t have to reload the whole page. The Pages simply display the new content as soon as it has loaded the content. GMail makes heavy use of Ajax.</p> <h2>Hierarchical Labels</h2> <p>Well, I guess this is less a technology than an idea. I think it would be gread if labels were used more often. I’d like to sort my personal files with labels, not with folders. The advantage of labels in comparison with folders is that you can add any number of labels to one object (file, e-mail, …). But you can have a file only in one path if you don’t copy the file. So you have to know how the person is thinking, if you want to find the file you are searching for.</p> <p>Example: You search for a file about you favorite books. Unfortunately, you don’t remember if it was an Excel-file or a Word-file. Now you have this tree structure:</p> <ul> <li>Excel</li> <li>Documents <ul> <li>School</li> <li>E-mails</li> <li>eBooks</li> <li>Math</li> </ul> </li> <li>School <ul> <li>Biology</li> <li>Chemistry</li> <li>English</li> <li>Math</li> </ul> </li> <li>Word</li> </ul> <p>The document you a re searching for could be in Word; in School/English, in Documents/eBooks or in Excel. You you had labels for your files, you could just select the files with a “Books”-label.</p> <p>I wrote “Hierarchical Labels”, because sometimes you have one label, that comes always with another one, but not the other way round. As I am not very interested in chemistry, all files about chemistry were for school. So if I tagged a file with “chemistry” it should automatically get the “school”-tag.</p> <div style="width: 73px" class="wp-caption alignright"><a href="../images/2011/10/Gravatar-Logo.png"><img src="../images/2011/10/Gravatar-Logo.png" alt="Gravatar-Logo" width="" height="" class="size-full wp-image-4441" /></a><p class="wp-caption-text">Gravatar-Logo</p></div> <h2>Gravatar</h2> <p>Have you ever noticed <a href="http://www.sembeo.com/ninja/comment-page-2/" rel="nofollow">blogs</a> or <a href="http://stackoverflow.com/questions/4880891/javascript-settimeout-and-changes-to-system-time-cause-problems" rel="nofollow">other</a> sites where some people have avatars and others don’t? Sometimes, if a possibility to login is provided this is not really amazing. But where does the website get the pictures from if there is no possibility to log in?</p> <p><a href="http://en.wikipedia.org/wiki/Gravatar" rel="nofollow">Gravatar</a> (an abbreviation for globally recognized avatar) is a service for providing globally-unique avatars. This is good for any website, where you don’t have the possibility to store large amounts of data or you don’t want to be annoyed with different file types, resizing and users who can’t manage to use your software.</p> <p><a href="http://lea.verou.me/demos/gravatar.php?email=info%40martin-thoma.de">Here</a> is a web service, that allows you to quickly see the Gravatars of one e-mail address.</p> <h2> Links for developers</h2> <ul> <li><a href="http://openid.net/developers/libraries/" rel="nofollow">OpenID libraries</a></li> <li><a href="http://de.gravatar.com/site/implement/hash/" rel="nofollow">Working with Gravatar</a></li> <li><a href="http://www.petefreitag.com/item/465.cfm" rel="nofollow">Howto Create an RSS 2.0 Feed</a></li> </ul> Clip: What Light //martin-thoma.com/clip-what-light/ Tue, 04 Oct 2011 23:07:51 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/clip-what-light <iframe width="560" height="315" src="http://www.youtube.com/embed/5BnVtz92Ius?rel=0" frameborder="0" allowfullscreen=""></iframe> Comparing Dates in PHP and MySQL //martin-thoma.com/comparing-dates-in-php-and-mysql/ Tue, 04 Oct 2011 20:22:12 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/comparing-dates-in-php-and-mysql <p>Sometimes you need to know compare PHP dates. You need to know what is later or if both dates are the same.</p> <h2>PHP</h2> <h3>time formats and functions</h3> <p>PHP knows these time / date formats:</p> <ul> <li>UNIX Timestamp: Integer - The number of seconds after 1970. Related functions are <ul> <li>int <a href="http://www.php.net/manual/en/function.mktime.php">`mktime([ int \`$hour = date("H") [, int \$`minute = date("i") [, int \`$second = date("s") [, int \$`month = date("n") [, int \`$day = date("j") [, int \$`year = date("Y") [, int \`$is_dst = -1 ]]]]]]])`</a></li> <li>int <a href="http://www.php.net/manual/en/function.time.php">`time()`</a></li> <li>string <a href="http://www.php.net/manual/en/function.date.php">`date( string \$`format [, int `$timestamp = time() ] )`</a></li> <li>int <a href="http://www.php.net/manual/en/function.strtotime.php">`strtotime( string \$`time [, int \`$now ] )`</a> I recommend using `YYYY-MM-DD HH:mm:ss` if possible.</li> </ul> </li> <li>Associative Arrays. The array looks like this ```php Array ( [year] =&gt; 2006 [month] =&gt; 12 [day] =&gt; 12 [hour] =&gt; 10 [minute] =&gt; 0 [second] =&gt; 0 [fraction] =&gt; 0.5 [warning_count] =&gt; 0 [warnings] =&gt; Array() [error_count] =&gt; 0 [errors] =&gt; Array() [is_localtime] =&gt; ) ``` The related functions are: <ul> <li>array <a href="http://www.php.net/manual/en/function.date-parse.php">date_parse</a> (string $`date)</li> <li>array <a href="http://php.net/manual/en/function.getdate.php">getdate</a> ([ int `$timestamp = time() ] )</li> </ul> </li> <li><a href="http://php.net/manual/en/class.datetime.php">DateTime Class</a>: This class can do quite a lot. You should read the manual if you're interested in using it.</li> </ul> <h3>Comparisons</h3> <p>Comparing UNIX Timestamps is like comparing integers. No problem.</p> <p>Comparing Arrays is more interesting. What do you think will the following script print?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#950">$d1</span> = date_parse (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">2011-05-11</span><span style="color:#710">&quot;</span></span>); <span style="color:#950">$d2</span> = date_parse (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">2011-05-11 13:00:00</span><span style="color:#710">&quot;</span></span>); <span style="color:#369;font-weight:bold">print_r</span>(<span style="color:#950">$d1</span>); <span style="color:#369;font-weight:bold">print_r</span>(<span style="color:#950">$d2</span>); <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$d1</span> &lt; <span style="color:#950">$d2</span>) { <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">$d1 is less than $d2.</span><span style="color:#710">'</span></span>; } <span style="color:#080;font-weight:bold">else</span> <span style="color:#080;font-weight:bold">if</span> (<span style="color:#950">$d1</span> == <span style="color:#950">$d2</span>) { <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">$d1 is equal to $d2.</span><span style="color:#710">'</span></span>; } <span style="color:#080;font-weight:bold">else</span> { <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">$d1 is greater than $d2.</span><span style="color:#710">'</span></span>; } <span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>It prints ‘$<code>d1 is less than </code>$d2.’ as</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>date_parse (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">2011-05-11</span><span style="color:#710">&quot;</span></span>); </pre></div> </div> </div> <p>is basically the same as</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>date_parse (<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">2011-05-11 00:00:00</span><span style="color:#710">&quot;</span></span>); </pre></div> </div> </div> <p>You can compare the Array to an integer, but I don’t know what PHP does. It seems as if the array would always be considered as beeing greater. If you use the functions you’ll be fine.</p> <h2>MySQL</h2> <h3>time formats and functions</h3> <p>MySQL knows these date and time <a href="http://dev.mysql.com/doc/refman/5.5/en/date-and-time-types.html">types</a> and those <a href="http://dev.mysql.com/doc/refman/5.5/en/date-and-time-functions.html">functions</a>. Here is a very short overview:</p> <ul> <li><a href="http://dev.mysql.com/doc/refman/5.5/en/datetime.html">DATETIME</a>: 'YYYY-MM-DD HH:MM:SS' range is from '1000-01-01 00:00:00' to '9999-12-31 23:59:59'</li> <li><a href="http://dev.mysql.com/doc/refman/5.5/en/datetime.html">DATE</a>: 'YYYY-MM-DD' range is from '1000-01-01' to '9999-12-31'</li> <li><a href="http://dev.mysql.com/doc/refman/5.5/en/datetime.html">TIMESTAMP</a>: like DATETIME, but range is from '1970-01-01 00:00:01' UTC to '2038-01-19 03:14:07' UTC</li> </ul> <p>Those examples show more than a long explanation:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">mysql&gt; SELECT CURTIME<span class="o">()</span><span class="p">;</span> -&gt; <span class="s1">&#39;23:50:26&#39;</span> <span class="c"># Adding zero will NOT convert it to a UNIX timestamp:</span> mysql&gt; SELECT CURTIME<span class="o">()</span> + 0<span class="p">;</span> -&gt; 235026.000000 <span class="c"># An &quot;integered&quot; TIME</span> mysql&gt; SELECT NOW<span class="o">(</span> <span class="o">)</span> -&gt; <span class="s1">&#39;2011-10-04 18:33:45&#39;</span> <span class="c"># Adding zero is a bad idea here, too:</span> mysql&gt; SELECT NOW<span class="o">(</span> <span class="o">)</span> +0 -&gt; 20111004190945.000000 <span class="c"># An &quot;integered&quot; DATETIME</span> <span class="c"># If you want a UNIX Timestamp, use this function</span> mysql&gt; SELECT UNIX_TIMESTAMP<span class="o">()</span><span class="p">;</span> -&gt; 1317746025 mysql&gt; SELECT UNIX_TIMESTAMP<span class="o">(</span><span class="s1">&#39;2011-10-04 18:33:45&#39;</span><span class="o">)</span><span class="p">;</span> -&gt; 1317746025 <span class="c"># You can also convert it:</span> mysql&gt; SELECT UNIX_TIMESTAMP<span class="o">(</span><span class="sb">`</span>my_datetime_row<span class="sb">`</span><span class="o">)</span> FROM <span class="sb">`</span>my_table<span class="sb">`</span></code></pre></div> <h3>Comparisons</h3> <p>You can compare two DATETIMEs like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_row</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_table</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHEN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">datetime1</span><span style="color:#710">`</span></span> &lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">datetime2</span><span style="color:#710">`</span></span> </pre></div> </div> </div> <p>It’s of course not problem if you compare two UNIX Timestamps which are stored as integers in the database:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_row</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_table</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHEN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">int1</span><span style="color:#710">`</span></span> &lt; <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">int2</span><span style="color:#710">`</span></span> </pre></div> </div> </div> <p>But what happens if you compare a DATETIME with a Timestamp (integer)?</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_row</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_table</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHEN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">datetime1</span><span style="color:#710">`</span></span> &lt; UNIX_TIMESTAMP() </pre></div> </div> </div> <p>This is basically:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#B06;font-weight:bold">SELECT</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_row</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">FROM</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">my_table</span><span style="color:#710">`</span></span> <span style="color:#080;font-weight:bold">WHEN</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">`</span><span style="color:#D20">datetime1</span><span style="color:#710">`</span></span> &lt; <span style="color:#00D">1317750167</span> </pre></div> </div> </div> <p>And it compares the “integered” DATETIME 20111004210710 for 2011-10-04 21:07:10 with 1317750167. This is obviously crap. Don’t do it. Never. Instead you should convert your dates with UNIX_TIMESTAMP(your_datetime) or FROM_UNIXTIME(unix_timestamp).</p> <h2>Comparing MySQL types with PHP types</h2> <p>The simplest way to compare MySQL DATE formats with PHP types is using strtotime(…) or date(…) if needed. If you have a DATETIME and you want to know if it’s in the past, you can use</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">strtotime</span>(<span style="color:#950">$datetime</span>) &lt; <span style="color:#369;font-weight:bold">time</span>()) { <span style="color:#369;font-weight:bold">echo</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">$datetime is in the past.</span><span style="color:#710">'</span></span>; } </pre></div> </div> </div> <h2>From PHP to MySQL</h2> <p>If you have a date you got via an date input field and want to submit it to MySQL, just use this piece of code:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#950">$mysqlFormat</span> = <span style="color:#369;font-weight:bold">date</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">Y-m-d H:i:s</span><span style="color:#710">'</span></span>, <span style="color:#369;font-weight:bold">strtotime</span>(<span style="color:#369;font-weight:bold">$_POST</span>[<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">my_date</span><span style="color:#710">'</span></span>])); </pre></div> </div> </div> Motion of the sun //martin-thoma.com/motion-of-the-sun/ Sun, 02 Oct 2011 09:25:07 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/motion-of-the-sun <p>How is the sun moving, according to our latitude, the time of the day and the time of the year? Just take a look at <a href="http://astro.unl.edu/naap/motion3/animations/sunmotions.swf">astro.unl.edu</a> and find it out!</p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/Motions-of-the-sun.png"><img src="../images/2011/10/Motions-of-the-sun.png" alt="Motions of the sun" width="" height="" class="size-full wp-image-3601" /></a><p class="wp-caption-text">Motions of the sun</p></div> Compare Planet Sizes //martin-thoma.com/compare-planet-sizes/ Sat, 01 Oct 2011 11:29:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/compare-planet-sizes <p>The diameter of Mercury measures about 4880 km. Can you imagine how much that is? I could not. But with <a href="http://www.sciencenetlinks.com/interactives/messenger/psc/PlanetSize.html">www.sciencenetlinks.com</a> you can compare it with the earth:</p> <div style="width: 410px" class="wp-caption aligncenter"><a href="../images/2011/10/Planet-Size-Comparison.png"><img src="../images/2011/10/Planet-Size-Comparison.png" alt="Planet Size Comparison" width="" height="" class="size-full wp-image-3351" /></a><p class="wp-caption-text">Planet Size Comparison</p></div> <p>By the way, if you are interested in the universe, you should go to a <a href="http://en.wikipedia.org/wiki/Planetarium">planetarium</a>. You can search the next one with <a href="http://maps.google.com/maps?f=q&amp;source=s_q&amp;hl=de&amp;geocode=&amp;q=planetarium+in+england&amp;aq=&amp;sll=52.629729,-1.318359&amp;sspn=7.190682,19.753418&amp;ie=UTF8&amp;hq=planetarium&amp;hnear=England,+Vereinigtes+K%C3%B6nigreich&amp;ll=52.469397,-1.252441&amp;spn=7.553141,19.753418&amp;t=h&amp;z=6">maps.google.com</a>. In Augsburg (Germany) it costs less than going to a 3D-cinema, but the movie showen in the planetarium is in 3D.</p> Game: Z-Type //martin-thoma.com/game-z-type/ Sat, 01 Oct 2011 10:36:41 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/game-z-type <div style="width: 178px" class="wp-caption aligncenter"><a href="../images/2011/10/z-type-168x300.png"><img src="../images/2011/10/z-type-168x300.png" alt="Z-Type" width="" height="" class="size-medium wp-image-3311" /></a><p class="wp-caption-text">Z-Type</p></div> <p><b>Go to the Game</b>: <a href="http://www.phoboslab.org/ztype/" rel="nofollow">www.phoboslab.org/ztype</a> <b>Task</b>: Survive as long as possible <b>How to play</b>: Type the words which appear at the top as fast as possible. The ship shoots at the words. <b>My Record</b>: Final Score: 1505 with Accuracy of 94.2% <b>Programming</b>: This game is written in JavaScript with <a href="http://impactjs.com/" rel="nofollow">Impact</a>.</p> Facepalm //martin-thoma.com/facepalm/ Fri, 30 Sep 2011 14:22:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/facepalm <p>With the Internet came a lot of new words. <a href="http://en.wikipedia.org/wiki/Cyberculture">Cyberculture</a> could be one of them, <a href="http://en.wikipedia.org/wiki/Google_(verb)">Googling</a> or <a href="http://en.wikipedia.org/wiki/Hacktivism">Hacktivism</a> would be others.</p> <p>Did you know that the famous gesture of Piccard is called a <a href="http://en.wikipedia.org/wiki/Facepalm">Facepalm</a>?</p> <div style="width: 138px" class="wp-caption aligncenter"><a href="../images/2011/09/Piccard-Facepalm.jpg"><img src="../images/2011/09/Piccard-Facepalm.jpg" alt="Piccard Facepalm" width="" height="" class="size-full wp-image-3171" /></a><p class="wp-caption-text">Piccard Facepalm</p></div> <p>The same word seems to exist also in German, so I’m quite sure that the word is new. (Although the <a href="http://en.wikipedia.org/wiki/Duden">Duden</a> doesn’t know it.)</p> <p>Although the gesture itself is obviously old:</p> <div style="width: 404px" class="wp-caption aligncenter"><a href="../images/2011/09/Cain_Henri_Vidal_Tuileries.jpg"><img src="../images/2011/09/Cain_Henri_Vidal_Tuileries.jpg" alt="Cain by Henri Vidal, in the Tuileries Gardens, Paris, 1896" width="" height="" class="size-full wp-image-3181" /></a><p class="wp-caption-text"><a href="http://commons.wikimedia.org/wiki/File:Cain_Henri_Vidal_Tuileries.jpg">Cain</a> by Henri Vidal, in the Tuileries Gardens, Paris, 1896</p></div> If Computer Problems Were Real //martin-thoma.com/if-computer-problems-were-real/ Fri, 30 Sep 2011 13:39:27 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/if-computer-problems-were-real <p>Before the computer … … a memory was something you’ve lost with age … an application was for employment … a program was a TV show … a cursor used profanity … a keyboard was a piano … a web was a spiders home … a virus was the flue … a CD was a bank account … a hard drive was a long trip on the road … a mouse pad was where a mouse lived … a tree, leaf and root could be found in nature … a path was wa way and if you had a 3,5 inch floppy… … you hoped nobody found out.</p> <p>If you like this kind of humor, you might want to watch this video:</p> <iframe width="640" height="360" src="http://www.youtube.com/embed/kAG39jKi0lI?rel=0" frameborder="0" allowfullscreen=""></iframe> <p>Thanks to Javier Benek for <a href="http://www.flickr.com/photos/xbenek/2449405807/sizes/m/in/photostream/">the picture</a>.</p> Colorize your scripts output //martin-thoma.com/colorize-your-scripts-output/ Fri, 30 Sep 2011 08:59:59 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/colorize-your-scripts-output <p>The bash is very nice if you want to know exactly what your scripts are doing. Unfortunately, its almost always white colored text on a black background, without any accentuation. No bold text, nothing underlined and no colors are used.</p> <p>You can change this standard behaviour. You can add color to your output.</p> <p>This is the way you do it:</p> <p>The mini-program tput can initialize a terminal or query terminfo database. If you want to know more about it, you can take a look at the <a href="http://linux.die.net/man/1/tput">tput manpage</a>.</p> <h2>A quick example</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="c"># Text color variables</span> <span class="nv">txtred</span><span class="o">=</span><span class="sb">`</span><span class="k">$(</span>tput setaf 1<span class="k">)</span> <span class="c"># Red</span> <span class="nv">txtreset</span><span class="o">=</span><span class="nv">$`</span><span class="o">(</span>tput sgr0<span class="o">)</span> <span class="c"># Reset your text</span> <span class="nb">echo</span> <span class="s2">&quot;Roses are `${txtred}red$`{txtreset}.&quot;</span></code></pre></div> <p>Simply copy this example line by line and then you’ll see the expected example.</p> <p>A shorter way would be</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">echo</span> <span class="s2">&quot;Roses are `tput setaf 1`red`tput sgr0`.&quot;</span></code></pre></div> <h2>The sgr attribuge</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">tput sgr <span class="m">0</span> <span class="m">1</span> turn off standout<span class="p">;</span> turn on underline tput sgr <span class="m">0</span> <span class="m">0</span> turn off standout<span class="p">;</span> turn off underline tput sgr <span class="m">1</span> <span class="m">1</span> turn on standout<span class="p">;</span> turn on underline tput sgr <span class="m">1</span> <span class="m">0</span> turn on standout<span class="p">;</span> turn off underline tput sgr0 short <span class="k">for</span> sgr <span class="m">0</span> 0</code></pre></div> <h2>The setaf attribute</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">setaf <span class="m">1</span> Red setaf <span class="m">2</span> Green setaf <span class="m">3</span> Yellow setaf <span class="m">4</span> Blue setaf <span class="m">5</span> Purple setaf <span class="m">6</span> Cyan setaf <span class="m">7</span> Gray</code></pre></div> <h2>Misc</h2> <p>Make your text bold:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">tput bold</code></pre></div> <p>Reset your style:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">tput sgr0</code></pre></div> <h2>Advanced Example</h2> <p>Imagine you had a script which generated much output. All messages are important for you, but some are more important than others. You definitely want to see all “[ERROR]” output. So you want to apply a red and bold modification to the stream.</p> <p>This is the way how “[ERROR]” gets red and bold:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="sb">`</span>tput setaf 1<span class="sb">``</span>tput bold<span class="sb">`</span><span class="o">[</span>ERROR<span class="o">]</span><span class="sb">`</span>tput sgr0<span class="sb">`</span></code></pre></div> <p>You can test it with</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash"><span class="nb">echo</span> <span class="s2">&quot;`tput setaf 1``tput bold`[ERROR]`tput sgr0`&quot;</span></code></pre></div> <p>I’ve created a little python script called output.py for testing purposes. It simply outputs a quite long <a href="http://en.wikipedia.org/wiki/Lorem_ipsum">Lorem ipsum</a> text with some random [ERROR] messages.</p> <p>The next task is to replace the [ERROR] messages. The tool of my choice is sed. See the <a href="http://linux.die.net/man/1/sed">sed man page</a> for more information. The basic usage is</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sed <span class="s1">&#39;s/search/replace/&#39;</span></code></pre></div> <p>So we pipe the output to sed:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python output.py <span class="p">|</span> sed <span class="s1">&#39;s/\[ERROR\]/MYLOOOOOOOOOOOOOOOOOONGTEST/&#39;</span></code></pre></div> <p>And now we bring it all together:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python output.py <span class="p">|</span> sed <span class="s1">&#39;s/[ERROR]/`tput setaf 1``tput bold`[ERROR]`tput sgr0`/&#39;</span></code></pre></div> <p>Doesn’t work? Well, lets analyse it. Instead of replacing <code>tput setaf 1</code> it gets printed directly. This means, something we did prevented the bash of replacing our command. If you look carefully at the command, you might see that I used ‘ instead of “. If you change this, everything is fine:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">python output.py <span class="p">|</span> sed <span class="s2">&quot;s/\[ERROR\]/`tput setaf 1``tput bold`[ERROR]`tput sgr0`/&quot;</span></code></pre></div> <h2>Colorize C / C++ output</h2> <p>You need <a href="http://en.wikipedia.org/wiki/ANSI_escape_code">ANSI color codes</a>:</p> <div class="highlight"><pre><code class="language-c" data-lang="c"><span class="cp">#include &lt;stdio.h&gt;</span> <span class="kt">int</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[30m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;black?&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[31m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;red&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[32m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;lime&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[33m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;yellow&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[34m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;blue&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[35m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;gray&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[36m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;blue&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[37m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;light gray&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[38m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;black?&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[39m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;black?&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[41m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;red background&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[1;34m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;bold and blue&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[4m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;underlined&quot;</span><span class="p">);</span> <span class="n">printf</span><span class="p">(</span><span class="s">&quot;</span><span class="se">\\</span><span class="s">033[9m%s</span><span class="se">\\</span><span class="s">033[0m</span><span class="se">\n</span><span class="s">&quot;</span><span class="p">,</span> <span class="s">&quot;strike&quot;</span><span class="p">);</span> <span class="k">return</span> <span class="mi">0</span><span class="p">;</span> <span class="p">}</span></code></pre></div> <p>\033 is the ASCII 27 ESC character. It has to be followed by “[”. After that you can write one or two numbers separated by “;”. Then you have to write “m”. You can get back to standard output with “\033[0m”. The numbers 30–37 change the color, 4 is a single underline.</p> <p>I guess these will also work for Java, but I didn’t test it.</p> <p>Do you know what setaf or sgr stand for? Do you know further “terminal enhancement” tricks? Just leave a post!</p> CAPTCHA //martin-thoma.com/captcha/ Thu, 29 Sep 2011 09:20:35 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/captcha <p>Spam is really a problem if you have a WordPress blog, a forum or a guestbook. A very common approach to solve this problem are CAPTCHAs - <strong>C</strong>ompletely <strong>A</strong>utomated <strong>P</strong>ublic <strong>T</strong>uring test to tell <strong>C</strong>omputers and <strong>H</strong>umans <strong>A</strong>part.</p> <p>The idea behind CAPTCHAs is to give the spammer a problem which is hard to solve for a computer program but easy to solve for a human.</p> <p>Most CAPTCHAs are really boring. I tried to find different categories of them, but most you will find online are in the “Optical character recognition” category:</p> <h2>Optical character recognition</h2> <div style="width: 320px" class="wp-caption aligncenter"><a href="../images/2011/09/Web-Wiz-CAPTCHA.png"><img src="../images/2011/09/Web-Wiz-CAPTCHA.png" alt="Web Wiz CAPTCHA" width="" height="" class="size-full wp-image-2751" /></a><p class="wp-caption-text">Web Wiz CAPTCHA</p></div> <p>I hope nobody seriously pays the 6 Euro for <a href="http://www.webwiz.co.uk/web-wiz-captcha/demo/">Web Wiz</a>. As many very simple CAPTCHAs it lacks a support for blind people. It is quite easy to read for humans, but I guess also for bots. They always use only five random characters which are written in blue. They added some dots and straight lines to make segmentation more difficult. I guess they never tried to hack their own CAPTCHA. If they did, they should be aware that those small dots don’t change anything and the straight lines can easily be detected and removed. It also seems to me as if they only used one font.</p> <p>Google did some great work with <a href="http://www.google.com/recaptcha">reCAPTCHA</a>. I think I’ll write a longer post about this later, but to keep it short:</p> <ul> <li>They use the reader (or spammer) to digitalize the books they scan. So if someone uses very good algorithms to bypass their CAPTCHA, the spammer will help Google. This is a very nice way to end up in a win-win situation, isn't it?</li> <li>reCAPTCHA has also support for blind people.</li> <li>The characters you have to type in are actual words. This makes it a lot easier for humans to recognize the characters.</li> <li>reCAPTCHA is very easy to use. No need of <a href="http://php.net/manual/en/book.image.php">GD</a> or <a href="http://www.php.net/manual/en/book.imagick.php">ImageMagick</a>.</li> <li>If you can't read it, just reload it.</li> </ul> <p>Here is a screenshot of reCAPTCHA:</p> <div style="width: 348px" class="wp-caption aligncenter"><a href="../images/2011/09/reCAPTCHA.png"><img src="../images/2011/09/reCAPTCHA.png" alt="reCAPTCHA" width="" height="" class="size-full wp-image-2781" /></a><p class="wp-caption-text">reCAPTCHA</p></div> <p>Here is another “traditional” CAPTCHA example.</p> <div style="width: 229px" class="wp-caption aligncenter"><a href="../images/2011/09/SimpleCaptcha.png"><img src="../images/2011/09/SimpleCaptcha.png" alt="SimpleCaptcha" width="" height="" class="size-full wp-image-2831" /></a><p class="wp-caption-text"><a href="http://simplecaptcha.sourceforge.net/">SimpleCaptcha</a></p></div> <h2>KittenAuth</h2> <p>I have never seen a working demo of <a href="http://thepcspy.com/kittenauth/">KittenAuth</a>, but the idea is simple: You get 9 pictures and you’re supposed to spot the cats:</p> <div style="width: 392px" class="wp-caption aligncenter"><a href="../images/2011/09/kittenAuth-captcha.jpg"><img src="../images/2011/09/kittenAuth-captcha.jpg" alt="kittenAuth CAPTCHA" width="" height="" class="size-full wp-image-2891" /></a><p class="wp-caption-text">The KittenAuth system. Source: ThePCSpy.com</p></div> <p>Very simmiliar is <a href="http://research.microsoft.com/en-us/um/redmond/projects/asirra/">ASIRRA</a>:</p> <div style="width: 559px" class="wp-caption aligncenter"><a href="../images/2011/09/ASIRRA.png"><img src="../images/2011/09/ASIRRA.png" alt="ASIRRA" width="" height="" class="size-full wp-image-2941" /></a><p class="wp-caption-text">ASIRRA</p></div> <h2>Basic human knowledge</h2> <p>Another CAPTCHA-type is based on basic human knowledge. <a href="http://textcaptcha.com/">Text CAPTCHA</a> is an example for this type. They ask you questions like:</p> <ul> <li>Which of milk, hotel or brain is a body part?</li> <li>How many letters in "devotional"?</li> <li>The word "tamers" has which letter in 2nd position?</li> <li>Enter the smallest number of 28, thirteen, twenty, 60, fifty six or 78:</li> <li>Which of knee, leg, ear or ankle is above the waist?</li> </ul> <p>I don’t think this type is very good as the spammer has to do almost the same amount of work as the programmer. He has to parse the different types of questions, but I guess this isn’t too hard.</p> <p>He might just ask Google: <a href="http://www.google.com/search?q=what+is+7+minus+3+times+2%3F">what is 7 minus 3 times 2?</a> or <a href="http://www.google.com/search?q=the+number+of+horns+on+a+unicorn#sclient=psy-ab&amp;hl=de&amp;source=hp&amp;q=what+is+the+number+of+horns+on+a+unicorn+times+the+answer+to+life%2C+the+universe%2C+and+everything%3F&amp;pbx=1&amp;oq=what+is+the+number+of+horns+on+a+unicorn+times+the+answer+to+life%2C+the+universe%2C+and+everything%3F&amp;aq=f&amp;aqi=&amp;aql=&amp;gs_sm=e&amp;gs_upl=15192l15192l2l15913l1l1l0l0l0l0l281l281l2-1l1l0&amp;bav=on.2,or.r_gc.r_pw.r_cp.&amp;fp=1f755a13a5fe778&amp;biw=1366&amp;bih=630">what is the number of horns on a unicorn times the answer to life, the universe, and everything?</a>.</p> <div style="width: 266px" class="wp-caption aligncenter"><a href="../images/2011/09/egglue-Egglue-Semantic-CAPTCHA.png"><img src="../images/2011/09/egglue-Egglue-Semantic-CAPTCHA.png" alt="egglue - Egglue Semantic CAPTCHA" width="" height="" class="size-full wp-image-2801" /></a><p class="wp-caption-text"><a href="http://code.google.com/p/egglue/">egglue</a> - Egglue Semantic CAPTCHA</p></div> <h2>Mathematics</h2> <p>I’ve seen some CAPTCHAs asking for very basic math questions like the following one. They are very easy to bypass if you want to write a bot:</p> <div style="width: 222px" class="wp-caption aligncenter"><a href="../images/2011/09/CAPTCHA-Basic-mathematics.png"><img src="../images/2011/09/CAPTCHA-Basic-mathematics.png" alt="CAPTCHA - Basic mathematics" width="" height="" class="size-full wp-image-2761" /></a><p class="wp-caption-text">CAPTCHA - Basic mathematics (<a href="http://mylittlehomepage.net/demos/captcha/index_math.php">example</a>)</p></div> <p>Sometimes they are not that easy:</p> <div style="width: 530px" class="wp-caption aligncenter"><a href="../images/2011/09/Rosocosmos.jpg"><img src="../images/2011/09/Rosocosmos.jpg" alt="Rosocosmos CAPTCHA" width="" height="" class="size-full wp-image-2901" /></a><p class="wp-caption-text">Rosocosmos CAPTCHA - Found on <a href="http://haunty.hubpages.com/hub/22-Funny-Captchas">hubpages.com</a></p></div> <div style="width: 366px" class="wp-caption aligncenter"><a href="../images/2011/09/Hard-math-CAPTCHA.png"><img src="../images/2011/09/Hard-math-CAPTCHA.png" alt="Hard math CAPTCHA" width="" height="" class="size-full wp-image-2921" /></a><p class="wp-caption-text">Hard math CAPTCHA - found on <a href="http://random.irb.hr/signup.php">random.irb.hr</a></p></div> <h2>Social CAPTCHA</h2> <p>I’ve just found Facebooks social CAPTCHA. I didn’t read <a href="http://blog.facebook.com/blog.php?post=486790652130">the article</a>. I guess the idea is that you know the name of your friends, but a stranger doesn’t. I had the same idea for a school website where you would have been forced to know the name of the teachers. Here is the example:</p> <div style="width: 549px" class="wp-caption aligncenter"><a href="../images/2011/09/Social-CAPTCHA.png"><img src="../images/2011/09/Social-CAPTCHA.png" alt="Social CAPTCHA" width="" height="" class="size-full wp-image-2851" /></a><p class="wp-caption-text">Social CAPTCHA</p></div> <h2>PLAYTHRU</h2> <p>To get through this CAPTCHA, you have to play a short game.</p> <div style="width: 370px" class="wp-caption aligncenter"><a href="../images/2011/09/playthru-1.png"><img src="../images/2011/09/playthru-1.png" alt="PLAYTHRU" width="" height="" class="size-full wp-image-43001" /></a><p class="wp-caption-text">PLAYTHRU</p></div> <div style="width: 370px" class="wp-caption aligncenter"><a href="../images/2011/09/playthru-2.png"><img src="../images/2011/09/playthru-2.png" alt="PLAYTHROU" width="" height="" class="size-full wp-image-43011" /></a><p class="wp-caption-text">PLAYTHROU</p></div> <p>You can get <a href="http://areyouahuman.com/">PLAYTHRU</a> here.</p> <h2>Further reading</h2> <ul> <li>Fun: <ul> <li>xkcd: <a href="http://xkcd.com/233/">A New CAPTCHA Approach</a></li> <li><a href="http://www.smosh.com/smosh-pit/photos/24-wtf-captchas">24 WTF Captchas</a></li> <li><a href="http://www.smosh.com/PC/smosh-pit/photos/25-very-naughty-facebook-captchas">25 Very Naughty Facebook Captchas</a></li> </ul> </li> <li>Free CAPTCHA systems: <ul> <li><a href="http://www.google.com/recaptcha">reCAPTCHA</a>: I recommend this one.</li> <li><a href="http://code.google.com/p/cool-php-captcha/">cool php captcha</a></li> <li><a href="http://www.1stwebdesigner.com/freebies/captcha-solutions-kill-spam/">Fight with Spam: 15+ Free Captcha Solutions</a></li> </ul> </li> <li>Breaking or creating CAPTCHAs: <ul> <li><a href="http://www.blackhat-seo.com/2008/how-to-break-captchas/">How to break captchas</a></li> <li><a href="http://caca.zoy.org/wiki/PWNtcha">PWNtcha</a></li> <li><a href="http://www.scribd.com/doc/24497942/Strong-CAPTCHA-Guidelines-v1-2">Strong CAPTCHA Guidelines</a></li> </ul> </li> </ul> Shortfilms //martin-thoma.com/shortfilms/ Wed, 28 Sep 2011 12:05:29 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/shortfilms <div class="info">Here is the second part "<a href="../shortfilms-part-ii/">Shortfilms, Part II</a>".</div> <h2>Turbo</h2> <iframe src="http://player.vimeo.com/video/6932347?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <p>TURBO is a high adrenaline short film in the tradition of The Karate Kid and Tron. It tells the story of Hugo Park (<a href="http://en.wikipedia.org/wiki/Justin_Chon">Justin Chon</a>, Twilight) a troubled youth whose only outlet for angst is a 4D fighting videogame called &ldquo;Super Turbo Arena&rdquo;. When Pharaoh King (<a href="http://en.wikipedia.org/wiki/Jocko_Sims">Jocko Sims</a>, Crash the Series), the Michael Jordan of cyber-sports, announces a tournament to determine who will join his pro-team, Hugo sets his eyes on the prize. But, Hugo isn't the only gamer who wants fame and glory. If Hugo wants to win he's going to have to beat Shamus (David Lehre, Epic Movie), the all time Turbo champ at the local Pandemonium arcade, and Ruse Kapri, a feisty prep girl that knows how to win. Realizing he can't win on his skill alone, Hugo turns to his brother Tobias a former kick-boxer whose last match left him wheel-chair ridden. Together the two will mend old wounds and see if a washed up street fighter can teach a troubled teen how to become a virtual gladiator!</p> <p>Here is the <a href="http://www.imdb.com/title/tt1448608/">imdb-entry</a>.</p> <h2>The Raven</h2> <iframe src="http://player.vimeo.com/video/11099712?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <p>THE RAVEN<br /> <br /> Chris Black possesses a power that could lead to the destruction of the current regime, and they will stop at nothing to destroy him. <br /> The chase is on as Chris runs for his life in this sci-fi thriller set in an alternate and futuristic Los Angeles.</p> <p>Here is the <a href="http://www.imdb.com/title/tt1646231/">imdb-entry</a>.</p> <h2>The Cat Piano</h2> <iframe src="http://player.vimeo.com/video/3985019?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" allowfullscreen=""></iframe> <p>Here is the <a href="http://www.imdb.com/title/tt1401657/">imdb-entry</a>.</p> <h2>The Ghastly Gourmet Cooking Show</h2> <iframe src="http://player.vimeo.com/video/4739045?title=0&amp;byline=0&amp;portrait=0" width="512" height="384" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <p>Who do you call when there's a catering catastrophe? The Ghastly Gourmet team of course! Chip, Chop and Chunk are three beastly little chefs who can make a meal of (and out of) any situation, no matter how monstrous the request. It's a gleefully gross cooking show not for the feint hearted or weak stomached!</p> <h2>Karma Currency - Charity Gift Vouchers</h2> <iframe src="http://player.vimeo.com/video/2366178?title=0&amp;byline=0&amp;portrait=0" width="512" height="289" frameborder="0" webkitallowfullscreen="" allowfullscreen=""></iframe> <h2>Sebastian's Voodoo</h2> <iframe src="http://player.vimeo.com/video/3534334?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <p>A voodoo doll must find the courage to save his friends from being pinned to death.</p> <h2>On Time</h2> <iframe src="http://player.vimeo.com/video/1198048?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe> <p>A travelling salesman selling the future in his suitcase.</p> 10 Great Videos on Vimeo //martin-thoma.com/10-great-videos-on-vimeo/ Wed, 28 Sep 2011 11:55:23 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/10-great-videos-on-vimeo <p>Vimeo is a video-sharing website like YouTube. The most obvious difference is the quality.</p> <p>Vimeo has over 3 million members.</p> <p>About 16,000 new videos get uploaded daily.</p> <p>Roughly 10% of all uploads are in HD.</p> <p>Here are 10 Great Videos I’ve found on Vimeo:</p> <h2>Ben Goldacre: Bad Science</h2> <iframe src="http://player.vimeo.com/video/17889555?title=0&amp;byline=0&amp;portrait=0&amp;color=006666" width="512" height="288" frameborder="0"></iframe> <h2>Thought of You</h2> <iframe src="http://player.vimeo.com/video/14803194?title=0&amp;byline=0&amp;portrait=0&amp;color=ffffff" width="512" height="288" frameborder="0"></iframe> <h2>Captain Awesome</h2> <iframe src="http://player.vimeo.com/video/18047390?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2>The Saga of Biorn</h2> <iframe src="http://player.vimeo.com/video/18011143?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2>The Blackwater Gospel</h2> <iframe src="http://player.vimeo.com/video/17914974?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2>Aurora Borealis</h2> <iframe src="http://player.vimeo.com/video/16917950?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2>Iceland, Eyjafjallaj&ouml;kull</h2> <iframe src="http://player.vimeo.com/video/11673745?title=0&amp;byline=0&amp;portrait=0" width="512" height="256" frameborder="0"></iframe> <h2>Rabbitkadabra!</h2> <iframe src="http://player.vimeo.com/video/24192252?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2>Eye Of The Storm</h2> <iframe src="http://player.vimeo.com/video/19659763?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2>Salesman Pete</h2> <iframe src="http://player.vimeo.com/video/15126262?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> Lolcats: Hermes' Favorite Activity //martin-thoma.com/lolcats-hermes-favorite-activity/ Mon, 26 Sep 2011 09:45:45 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/lolcats-hermes-favorite-activity <p>Cats are sometimes so crazy.</p> <p>This cat obviously loves beeing thrown on a bed.</p> <p>Have fun with the Lolcat-Clip:</p> <iframe width="560" height="315" src="http://www.youtube.com/embed/kYSoy71ib7A?rel=0" frameborder="0" allowfullscreen=""></iframe> Game: Winterbells //martin-thoma.com/game-winterbells/ Sun, 25 Sep 2011 10:12:43 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/game-winterbells <p><b>Go to the Game</b>: <a href="http://www.ferryhalim.com/orisinal/g3/bells.htm" rel="nofollow">www.ferryhalim.com</a> <b>Task</b>: Jump at as many bells / pigeons with your arctic hare as possible <b>How to play</b>: The arctic hare jumps automatically. You choose the direction in which he jumps / flies with your mouse. <b>My Record</b>: 44,960</p> <p>If you thought that was good, just watch this video:</p> <iframe title="YouTube video player" width="512" height="414" src="http://www.youtube.com/embed/mcrMDeeERks?rel=0&amp;hd=1" frameborder="0" allowfullscreen=""></iframe> Game: Lightbot 2.0 //martin-thoma.com/game-lightbot-2-0/ Sun, 25 Sep 2011 10:08:27 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/game-lightbot-2-0 <div style="width: 310px" class="wp-caption aligncenter"><a href="../images/2011/09/Lightbot-2.0-300x171.png"><img src="../images/2011/09/Lightbot-2.0-300x171.png" alt="" width="" height="" class="size-medium wp-image-2171" /></a><p class="wp-caption-text">Lightbot 2.0</p></div> <p><b>Go to the Game</b>: <a href="http://www.kongregate.com/games/Coolio_Niato/lighbot-2-0">Lightbot 2.0 on Kongregate</a> <b>Task</b>: Solve the levels <b>How to play</b>: You can programm the Lightbot to move, jump and to switch its light on. By defining functions and using recursion you can keep your program code small. It’s a nice online game where you can start to learn programming. <b>My Record</b>: All Basic and Recursion-Levels done.</p> Using Wikipedia as a Newssstream //martin-thoma.com/using-wikipedia-as-a-newssstream/ Sat, 24 Sep 2011 23:21:23 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/using-wikipedia-as-a-newssstream <p>I am very interested in the development of Google+. As I am also quite active on Wikipedia (just take a look at my <a href="http://toolserver.org/~soxred93/pcount/index.php?name=MartinThoma&amp;lang=de&amp;wiki=wikipedia">edit counter</a>) I add all topics in which I am interested in to my personal watchlist. I added the RSS-Feed to my feed reader. So I get instantly a little pop-up as soon as the article changes. Great.</p> <p>…</p> <p>if there wouldn’t be so many reverts / minor edits. Most edits I get informed of are either bot-edits (The article is now available in Tiếng Việt! Fantastic!) or simply reverted after a few hours.</p> <p>I’m searching for a tool which reads my feed and generates a new feed. This new feed should contain only messages when relevant changes were made. Does something like this already exist? Does somebody want to invent such a web service?</p> <p>At the moment I don’t have the time to do it myself, so I tagged this post with “idea”. If you’re searching for an idea for a new project, just take a look at those topics.</p> Joke: Electrical Engineering vs. Computer Science //martin-thoma.com/joke-electrical-engineering-vs-computer-science/ Sat, 24 Sep 2011 22:29:05 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/joke-electrical-engineering-vs-computer-science <div style="width: 138px" class="wp-caption alignright"><a href="../images/2011/09/Nerd-Crossing.jpg"><img src="../images/2011/09/Nerd-Crossing.jpg" alt="Nerd-Crossing" width="" height="" class="size-full wp-image-2071" /></a><p class="wp-caption-text">Nerd-Crossing</p></div> <p>I’ve just stumbled upon this joke on <a href="http://wilk4.com/humor/humore2.htm">wilk4.com</a>. This is the reason why I didn’t use OOP in any of my (small) projects and why I don’t understand those people who want every piece of code in OOP-style:</p> <p>Once upon a time, in a kingdom not far from here, a king summoned two of his advisors for a test. He showed them both a shiny metal box with two slots in the top, a control knob, and a lever. “What do you think this is?”</p> <p>One advisor, an <strong>engineer</strong>, answered first. “It is a toaster,” he said. The king asked, “How would you design an embedded computer for it?” The engineer replied, “Using a four-bit microcontroller, I would write a simple program that reads the darkness knob and quantizes its position to one of 16 shades of darkness, from snow white to coal black. The program would use that darkness level as the index to a 16-element table of initial timer values. Then it would turn on the heating elements and start the timer with the initial value selected from the table. At the end of the time delay, it would turn off the heat and pop up the toast. Come back next week, and I’ll show you a working prototype.”</p> <p>The second advisor, a <strong>computer scientist</strong>, immediately recognized the danger of such short-sighted thinking. He said, “Toasters don’t just turn bread into toast, they are also used to warm frozen waffles. What you see before you is really a breakfast food cooker. As the subjects of your kingdom become more sophisticated, they will demand more capabilities. They will need a breakfast food cooker that can also cook sausage, fry bacon, and make scrambled eggs. A toaster that only makes toast will soon be obsolete. If we don’t look to the future, we will have to completely redesign the toaster in just a few years.”</p> <p>“With this in mind, we can formulate a more intelligent solution to the problem. First, create a class of breakfast foods. Specialize this class into subclasses: grains, pork, and poultry. The specialization process should be repeated with grains divided into toast, muffins, pancakes, and waffles; pork divided into sausage, links, and bacon; and poultry divided into scrambled eggs, hard- boiled eggs, poached eggs, fried eggs, and various omelet classes.”</p> <p>“The ham and cheese omelet class is worth special attention because it must inherit characteristics from the pork, dairy, and poultry classes. Thus, we see that the problem cannot be properly solved without multiple inheritance. At run time, the program must create the proper object and send a message to the object that says, ‘Cook yourself.’ The semantics of this message depend, of course, on the kind of object, so they have a different meaning to a piece of toast than to scrambled eggs.”</p> <p>“Reviewing the process so far, we see that the analysis phase has revealed that the primary requirement is to cook any kind of breakfast food. In the design phase, we have discovered some derived requirements. Specifically, we need an object-oriented language with multiple inheritance. Of course, users don’t want the eggs to get cold while the bacon is frying, so concurrent processing is required, too.”</p> <p>“We must not forget the user interface. The lever that lowers the food lacks versatility, and the darkness knob is confusing. Users won’t buy the product unless it has a user-friendly, graphical interface. When the breakfast cooker is plugged in, users should see a cowboy boot on the screen. Users click on it, and the message ‘Booting UNIX v.8.3’ appears on the screen. (UNIX 8.3 should be out by the time the product gets to the market.) Users can pull down a menu and click on the foods they want to cook.”</p> <p>“Having made the wise decision of specifying the software first in the design phase, all that remains is to pick an adequate hardware platform for the implementation phase. An Intel 80386 with 8MB of memory, a 30MB hard disk, and a VGA monitor should be sufficient. If you select a multitasking, object oriented language that supports multiple inheritance and has a built-in GUI, writing the program will be a snap. (Imagine the difficulty we would have had if we had foolishly allowed a hardware-first design strategy to lock us into a four-bit microcontroller!).”</p> <p>The king wisely had the computer scientist beheaded, and they all lived happily ever after.</p> Google Ngram Viewer //martin-thoma.com/google-ngram-viewer/ Sat, 24 Sep 2011 19:02:34 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/google-ngram-viewer <p>On October 14, 2010 Google announced that the number of scanned books is over 15 million. They did not simply scan those books, but they digitalized them. They can access not only image files, but the actual text. This allowes Google to search in those books and to analyse the information.</p> <p>Google has processed 1,024,908,267,229 words of running text and is publishing the counts for all 1,176,470,663 five-word sequences that appear at least 40 times. One five-word-sequence would be a five-gram, a four-word-sequence a four-gram.</p> <p>Google has published the Ngram Viewer. This is a tool which allows the user to specify some Ngrams and search how often they appear over the years.</p> <p>Here is an example search:</p> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Google-Ngram-Viewer-germany-france-300x113.png"><img src="../images/2011/09/Google-Ngram-Viewer-germany-france-300x113.png" alt="Google Ngram Viewer: Germany vs France" width="" height="" class="size-medium wp-image-1971" /></a><p class="wp-caption-text">Google Ngram Viewer: Germany vs France</p></div> <p>The x-axis shows the years, the y-axis shows the percentage of the specified ngram of all ngrams. Don’t bother with the numbers. If one curve is higher than the other, more books contained the specified Ngram.</p> <p>My example shows that the term “France” was more often in books than “Germany”. Why is this the case? My first thought was that in the time of the two world wars more books should have been written about Germany. The answer is simply that I wrote “germany” instead of “Germany”. So it’s case sensitive:</p> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Google-Ngram-Viewer-Germany-France-Third-Reich-300x112.png"><img src="../images/2011/09/Google-Ngram-Viewer-Germany-France-Third-Reich-300x112.png" alt="Google Ngram Viewer: Germany vs. France vs. Third-Reich" width="" height="" class="size-medium wp-image-1981" /></a><p class="wp-caption-text">Google Ngram Viewer: Germany vs. France vs. Third-Reich</p></div> <p>You can compare how successfull some books are:</p> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Google-Ngram-Viewer-Harry-Potter-Lord-of-the-Rings-The-Da-Vinci-Code-300x112.png"><img src="../images/2011/09/Google-Ngram-Viewer-Harry-Potter-Lord-of-the-Rings-The-Da-Vinci-Code-300x112.png" alt="Google Ngram Viewer: Harry Potter vs. Lord of the Rings vs. The Da Vinci Code" width="" height="" class="size-medium wp-image-2001" /></a><p class="wp-caption-text">Google Ngram Viewer: Harry Potter vs. Lord of the Rings vs. The Da Vinci Code</p></div> <p>Quite interesting is also the interest in famous physicists:</p> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Google-Ngram-Viewer-Physics-300x113.png"><img src="../images/2011/09/Google-Ngram-Viewer-Physics-300x113.png" alt="Google Ngram Viewer: Famous physicists" width="" height="" class="size-medium wp-image-2011" /></a><p class="wp-caption-text">Google Ngram Viewer: Famous physicists</p></div> <p>You can try all sort of things:</p> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Google-Ngram-Viewer-Happy-300x111.png"><img src="../images/2011/09/Google-Ngram-Viewer-Happy-300x111.png" alt="Google Ngram Viewer: Happy" width="" height="" class="size-medium wp-image-2031" /></a><p class="wp-caption-text">Google Ngram Viewer: Happy</p></div> <p>Did you get some interesting results? Please post a link!</p> <h2>Sources</h2> <ul> <li><a title="Google Books" href="http://en.wikipedia.org/wiki/Google_Books">Google Books</a>. Recieved 24 September 2011.</li> <li><a href="http://googleresearch.blogspot.com/2006/08/all-our-n-gram-are-belong-to-you.html">All Our N-gram are Belong to You</a>. Recieved 24 September 2011.</li> <li>Video: <a href="http://www.ted.com/talks/what_we_learned_from_5_million_books.html">What we learned from 5 million books</a>.</li> </ul> Python: Check Wiki-references for citation template //martin-thoma.com/python-check-wiki-references-for-citation-template/ Sat, 24 Sep 2011 11:39:40 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/python-check-wiki-references-for-citation-template <p>Wikipedia articles are full of references. Those references should be formatted the same way. It is much easier to use a template for citations than trying to guess the right way how to cite. Unfortunately most wikipedia users don’t know the <a href="http://en.wikipedia.org/wiki/Template:Citation" title="Template:Citation">Template:Citation</a>.</p> <p>So I try to fix all manual styled citations when I edit an article. Doing this manually is quite time intensive. This is the reason why I wrote a little Python-script.</p> <h2>Examples</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;ref&gt;</span>[http://peter.mapledesign.co.uk/weblog/archives/python-is-slow Python is... slow?] December 21st, 2004 <span style="color:#800;font-weight:bold">&amp;mdash;</span> Peter Bowyer<span style="color:#800;font-weight:bold">&amp;rsquo;</span>s weblog]<span style="color:#070;font-weight:bold">&lt;/ref&gt;</span> </pre></div> </div> </div> <p>should be</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;ref&gt;</span>{{Citation |url=http://peter.mapledesign.co.uk/weblog/archives/python-is-slow |title=Python is... slow? |accessdate=September 24, 2011}}<span style="color:#070;font-weight:bold">&lt;/ref&gt;</span> </pre></div> </div> </div> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;ref&gt;</span>[http://www.nongnu.org/pydbc/ Contracts for Python], PyDBC<span style="color:#070;font-weight:bold">&lt;/ref&gt;</span> </pre></div> </div> </div> <p>should be</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#070;font-weight:bold">&lt;ref&gt;</span>{{Citation |url=http://www.nongnu.org/pydbc/ |title=Contracts for Python |accessdate=September 24, 2011}}<span style="color:#070;font-weight:bold">&lt;/ref&gt;</span> </pre></div> </div> </div> <p>So, all that has to be done is</p> <ol> <li>Finding all <ref>-Tags without a template in one article <li>Trying to find the URL of this reference</li> <li>Filling out as much as possible for the user</li> <li>Asking the user for missing information</li> <li>Returning the new article wiki source code</li> <h2>Downloading wiki source code</h2> Wikipedia offers an <a href="http://en.wikipedia.org/w/api.php" title="Wikipedia API">API</a> for accessing the needed information. I will use this API and Pythons <a href="http://docs.python.org/library/optparse.html">optparse</a>, <a href="http://www.crummy.com/software/BeautifulSoup/documentation.html">BeautifulSoup</a> and <a href="http://docs.python.org/library/htmlparser.html">HTMLParser</a> to get the raw wiki text in UTF-8 encoding: ```python #!/usr/bin/python # -*- coding: utf-8 -*- import urllib2 from optparse import OptionParser from BeautifulSoup import BeautifulStoneSoup import HTMLParser parser = OptionParser() parser.add_option("-l", "--lemma", dest="lemma", default="Python", type="string", help="Which lemma should be checked?") parser.add_option("-m", "--language", dest="language", default="en", type="string", help="Which langauge should be used " + "(english wiki, geman wiki, ... )") parser.add_option("-v", "--verbose", action="store_true", dest="verbose", default=False, help="Show more information.") (options, args) = parser.parse_args() def load(lemma, language="en", format="xml"): """ Get the Wikipedia Source Text (not the HTML source code) format:xml,json, ... language:en, de, ... Returns None if page doesn't exist """ lemma = lemma.replace(" ", "_") url = 'http://' + language + '.wikipedia.org/w/api.php' + \ '?action=query&amp;format=' + format + \ '&amp;prop=revisions&amp;rvprop=content' + \ '&amp;titles=' + lemma request = urllib2.Request(url) handle = urllib2.urlopen(request) text = handle.read() if format == 'xml': soup = BeautifulStoneSoup(text) rev = soup.rev if rev != None: text = unicode(rev.contents[0]) text = HTMLParser.HTMLParser().unescape(text) text = text.encode( "utf-8" ) else: return None return text ``` We are now able to access the needed information. Now we need to get the references without templates. To do so, I will use the <a href="http://docs.python.org/library/re.html">Python re module</a>: ```python import re def getRef(page): """ Get all references without templates """ pattern = "(<ref>\[.+?</ref>)" prog = re.compile(pattern) m = re.findall(pattern, page) return m ``` Now the single references have to get parsed and the user has to confirm or edit the results: ```python import readline from datetime import date def rlinput(prompt, prefill=''): """ Promt the user for input, but prefill it. """ readline.set_startup_hook(lambda: readline.insert_text(prefill)) try: return raw_input(prompt) finally: readline.set_startup_hook() def improve(references, page): """ Try to guess the right formatation for each reference and ask the user to confirm or edit the formatation of the reference. """ urlPattern = "http.+? " urlPatternCompiled = re.compile(urlPattern) today = date.today() accessdate = str(today.strftime("%B %d, %Y")) for refOld in references: url = re.findall(urlPatternCompiled, refOld) refNew = "<ref>{{Citation " + \ "|url=" + str(url[0]) + \ "|title= " + \ "|accessdate=" + accessdate + \ "}}</ref>" refNew = rlinput(refOld + " (old):\n", refNew) page = page.replace(refOld, refNew) print "" return page ``` Here is the full script: ```python #!/usr/bin/python # -*- coding: utf-8 -*- import urllib2 from optparse import OptionParser from BeautifulSoup import BeautifulStoneSoup import HTMLParser import re import readline from datetime import date parser = OptionParser() parser.add_option("-l", "--lemma", dest="lemma", default="Python", type="string", help="Which lemma should be checked?") parser.add_option("-f", "--file", dest="filename", help="write corrected wiki source code to FILE", metavar="FILE", default="wikioutput.txt") parser.add_option("-m", "--language", dest="language", default="en", type="string", help="Which langauge should be used " + "(english wiki, geman wiki, ... )") parser.add_option("-v", "--verbose", action="store_true", dest="verbose", default=False, help="Show more information.") (options, args) = parser.parse_args() def load(lemma, language="en", format="xml"): """ Get the Wikipedia Source Text (not the HTML source code) format:xml,json, ... language:en, de, ... Returns None if page doesn't exist """ lemma = lemma.replace(" ", "_") url = 'http://' + language + '.wikipedia.org/w/api.php' + \ '?action=query&amp;format=' + format + \ '&amp;prop=revisions&amp;rvprop=content' + \ '&amp;titles=' + lemma request = urllib2.Request(url) handle = urllib2.urlopen(request) text = handle.read() if format == 'xml': soup = BeautifulStoneSoup(text) rev = soup.rev if rev != None: text = unicode(rev.contents[0]) text = HTMLParser.HTMLParser().unescape(text) text = text.encode( "utf-8" ) else: return None return text def getRef(page): """ Get all references without templates """ pattern = "(<ref>\[.+?</ref>)" prog = re.compile(pattern) m = re.findall(prog, page) return m def rlinput(prompt, prefill=''): """ Promt the user for input, but prefill it. """ readline.set_startup_hook(lambda: readline.insert_text(prefill)) try: return raw_input(prompt) finally: readline.set_startup_hook() def improve(references, page): """ Try to guess the right formatation for each reference and ask the user to confirm or edit the formatation of the reference. """ urlPattern = "http.+? " urlPatternCompiled = re.compile(urlPattern) today = date.today() accessdate = str(today.strftime("%B %d, %Y")) for refOld in references: url = re.findall(urlPatternCompiled, refOld) refNew = "<ref>{{Citation " + \ "|url=" + str(url[0]) + \ "|title= " + \ "|accessdate=" + accessdate + \ "}}</ref>" refNew = rlinput(refOld + " (old):\n", refNew) page = page.replace(refOld, refNew) print "" return page if __name__ == '__main__': print("If you need more parameters like 'date': " + \ "http://en.wikipedia.org/wiki/Template:Citation#" + \ "Full_citation_parameters") page = load(options.lemma) references = getRef(page) page = improve(references, page) f = open(options.filename, 'w') f.write(page) f.close() print("Page has been written to %s." % options.filename) ``` This can be improved in several ways: <ul> <li>Checking automatically the title / dead links</li> <li>Trying to find the publication date automatically</li> <li>Skip links with <a href="http://en.wikipedia.org/wiki/Template:Dead_link" title="Template:Dead link">Templade:Dead link</a></li> <li>Search also for <ref name="xyz">Text</ref></li> </ul> Here is the <a href="http://en.wikipedia.org/w/index.php?title=Python_%28programming_language%29&amp;action=historysubmit&amp;diff=452167384&amp;oldid=452164712">Wikipedia diff page</a>. My little script seems to work. </ref></li></ol> PHP: PEAR MDB2 //martin-thoma.com/pear-db/ Sat, 24 Sep 2011 01:38:35 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/pear-db <p>PEAR is short for <strong>P</strong>HP <strong>E</strong>xtension and <strong>A</strong>pplication <strong>R</strong>epository. It provides a very easy method to get some common classes.</p> <p>PEAR MDB2 is a database class. It is a successor of PEAR DB. I took a look at version 1.4.1 which is currently the latest stable one.</p> <h2>Install PEAR</h2> <p>You can install PEAR on Ubuntu via</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo apt-get install php-pear</code></pre></div> <p>You can check if it is installed with <a href="http://php.net/manual/en/function.phpinfo.php">phpinfo()</a>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="font-weight:bold;color:#666">&lt;?php</span> <span style="color:#369;font-weight:bold">phpinfo</span>();<span style="font-weight:bold;color:#666">?&gt;</span> </pre></div> </div> </div> <p>Something like <strong>.:/usr/share/php:/usr/share/pear</strong> should be in your <strong>include_path</strong>.</p> <h2>Install PEAR MDB2</h2> <p>PEAR MDB2 is then simply installed via</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo pear install MDB2</code></pre></div> <p>Then install the optional MySQL package:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo pear install pear/MDB2#mysql</code></pre></div> <h2>Usage</h2> <p>I took a small chess database to test this package. You can set it up with <a href="http://code.google.com/p/community-chess/source/browse/trunk/install/chess.sql?spec=svn99&amp;r=98">this sql file</a>.</p> <p>It’s sad, but only including <strong>MDB2.php</strong> shows 5 “Deprecated”-messages and 6 warings because of “Strict Standards”.</p> <p>You can easily connect to the database:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#369;font-weight:bold">require_once</span> <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">MDB2.php</span><span style="color:#710">&quot;</span></span>; <span style="color:#950">$db</span> = <span style="color:#080;font-weight:bold">new</span> <span style="color:#036;font-weight:bold">MDB2</span>(); <span style="color:#950">$dsn</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">mysql://chessuser:localpass@localhost/chess</span><span style="color:#710">&quot;</span></span>; <span style="color:#950">$mdb2</span> = <span style="color:#036;font-weight:bold">MDB2</span>::factory(<span style="color:#950">$dsn</span>); <span style="color:#950">$mdb2</span>-&gt;setFetchMode(<span style="color:#036;font-weight:bold">MDB2_FETCHMODE_ASSOC</span>); </pre></div> </div> </div> <p>It is also very easy to fetch some data:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#950">$sql</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">SELECT * FROM `chess_users`</span><span style="color:#710">'</span></span>; <span style="color:#950">$result</span> = <span style="color:#950">$mdb2</span>-&gt;query(<span style="color:#950">$sql</span>); <span style="color:#080;font-weight:bold">while</span> (<span style="color:#950">$row</span> = <span style="color:#950">$result</span>-&gt;fetchRow()) { <span style="color:#369;font-weight:bold">print_r</span>(<span style="color:#950">$row</span>); } </pre></div> </div> </div> <p>or</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#950">$sql</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">SELECT * FROM `chess_users`</span><span style="color:#710">'</span></span>; <span style="color:#950">$data</span> = <span style="color:#950">$mdb2</span>-&gt;queryAll(<span style="color:#950">$sql</span>); <span style="color:#369;font-weight:bold">print_r</span>(<span style="color:#950">$data</span>); </pre></div> </div> </div> <p>This results in:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>Array ( [user_id] =&gt; 1 [user_name] =&gt; abc [user_password] =&gt; 900150983cd24fb0d6963f7d28e17f72 [currentchesssoftware] =&gt; 0 ) Array ( [user_id] =&gt; 2 [user_name] =&gt; test [user_password] =&gt; 098f6bcd4621d373cade4e832627b4f6 [currentchesssoftware] =&gt; 0 ) </pre></div> </div> </div> <p>You can set limits via MDB2:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#950">$sql</span> = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">SELECT * FROM `chess_users`</span><span style="color:#710">'</span></span>; <span style="color:#950">$mdb2</span>-&gt;setLimit(<span style="color:#00D">1</span>); <span style="color:#950">$data</span> = <span style="color:#950">$mdb2</span>-&gt;queryAll(<span style="color:#950">$sql</span>); <span style="color:#369;font-weight:bold">print_r</span>(<span style="color:#950">$data</span>); </pre></div> </div> </div> <p>MDB2 offers lots of other features like choosing a (non)persistent connection, prepared statements or debuggin option. If you’re interested in PEAR MDB2 I recommend to take a look at installationwiki.org.</p> <h2>Sources</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/PEAR" title="PEAR">PEAR</a>. Recieved 24 September 2011.</li> <li><a href="http://pear.php.net/package/MDB2" title="PEAR MDB2">PEAR MDB2</a>. Recieved 24 September 2011.</li> <li><a href="http://www.installationwiki.org/MDB2">MDB2</a> on installationwiki.org. Recieved 24 September 2011.</li> </ul> Data Visualization //martin-thoma.com/data-visualization/ Fri, 23 Sep 2011 19:32:15 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/data-visualization <p>The United States public debt increased from `$10.7 trillion in 2008 to $`14.2 trillion by February 2011. Google processes about 24 petabytes of data per day. About 21.9 people live in Mumbai.</p> <p>Today it is incredibly easy to gain raw data, but without context they aren’t worth anything. You have to know some different information of the same context with which you can compare the given information.</p> <p>If I told you that 24 petabytes equals approximately 1,600 years of a high quality video you can get a feeling for the information. This can be done even better if you use graphical elements.</p> <p>Here are two great examples of data visualization.</p> <h2>David McCandless</h2> <object width="446" height="326"><param name="movie" value="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" /> <param name="allowFullScreen" value="true" /> <param name="allowScriptAccess" value="always" /> <param name="wmode" value="transparent" /> <param name="bgColor" value="#ffffff" /> <param name="flashvars" value="vu=http://video.ted.com/talks/dynamic/DavidMcCandless_2010G-medium.flv&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/DavidMcCandless-2010G.embed_thumbnail.jpg&amp;vw=432&amp;vh=240&amp;ap=0&amp;ti=937&amp;lang=&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=david_mccandless_the_beauty_of_data_visualization;year=2010;theme=presentation_innovation;theme=design_like_you_give_a_damn;theme=the_creative_spark;theme=a_taste_of_tedglobal_2010;event=TEDGlobal+2010;tag=Design;tag=complexity;tag=computers;tag=data;tag=visualizations;&amp;preAdTag=tconf.ted/embed;tile=1;sz=512x288;" /> <embed src="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" pluginspace="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" wmode="transparent" bgcolor="#ffffff" width="446" height="326" allowfullscreen="true" allowscriptaccess="always" flashvars="vu=http://video.ted.com/talks/dynamic/DavidMcCandless_2010G-medium.flv&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/DavidMcCandless-2010G.embed_thumbnail.jpg&amp;vw=432&amp;vh=240&amp;ap=0&amp;ti=937&amp;lang=&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=david_mccandless_the_beauty_of_data_visualization;year=2010;theme=presentation_innovation;theme=design_like_you_give_a_damn;theme=the_creative_spark;theme=a_taste_of_tedglobal_2010;event=TEDGlobal+2010;tag=Design;tag=complexity;tag=computers;tag=data;tag=visualizations;" /></object> <h2>Hans Rosling</h2> <object width="334" height="326"><param name="movie" value="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" /> <param name="allowFullScreen" value="true" /> <param name="allowScriptAccess" value="always" /> <param name="wmode" value="transparent" /> <param name="bgColor" value="#ffffff" /> <param name="flashvars" value="vu=http://video.ted.com/talks/dynamic/HansRosling_2006-medium.flv&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/HansRosling-2006.embed_thumbnail.jpg&amp;vw=320&amp;vh=240&amp;ap=0&amp;ti=92&amp;lang=&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=hans_rosling_shows_the_best_stats_you_ve_ever_seen;year=2006;theme=technology_history_and_destiny;theme=unconventional_explanations;theme=women_reshaping_the_world;theme=rethinking_poverty;theme=numbers_at_play;theme=presentation_innovation;event=TED2006;tag=Global+Issues;tag=Google;tag=africa;tag=asia;tag=demo;tag=development;tag=economics;tag=health;tag=statistics;tag=visualizations;&amp;preAdTag=tconf.ted/embed;tile=1;sz=512x288;" /> <embed src="http://video.ted.com/assets/player/swf/EmbedPlayer.swf" pluginspace="http://www.macromedia.com/go/getflashplayer" type="application/x-shockwave-flash" wmode="transparent" bgcolor="#ffffff" width="334" height="326" allowfullscreen="true" allowscriptaccess="always" flashvars="vu=http://video.ted.com/talks/dynamic/HansRosling_2006-medium.flv&amp;su=http://images.ted.com/images/ted/tedindex/embed-posters/HansRosling-2006.embed_thumbnail.jpg&amp;vw=320&amp;vh=240&amp;ap=0&amp;ti=92&amp;lang=&amp;introDuration=15330&amp;adDuration=4000&amp;postAdDuration=830&amp;adKeys=talk=hans_rosling_shows_the_best_stats_you_ve_ever_seen;year=2006;theme=technology_history_and_destiny;theme=unconventional_explanations;theme=women_reshaping_the_world;theme=rethinking_poverty;theme=numbers_at_play;theme=presentation_innovation;event=TED2006;tag=Global+Issues;tag=Google;tag=africa;tag=asia;tag=demo;tag=development;tag=economics;tag=health;tag=statistics;tag=visualizations;" /></object> <h2>Sources and furhter reading</h2> <ul> <li><a href="http://www.gapminder.org/">Gapminder</a>: A tool for data visualization.</li> <li><a href="http://en.wikipedia.org/wiki/United_States_public_debt">United States public debt.</a> Recieved 23 September 2011.</li> <li><a href="http://dl.acm.org/citation.cfm?doid=1327452.1327492" title="MapReduce">MapReduce.</a> Portal.acm.org. Retrieved 16 August 2009.</li> <li><a href="http://en.wikipedia.org/wiki/Mumbai" title="Mumbai">Mumbai.</a> Recieved 23 September 2009.</li> </ul> Cleverbot vs. Wolfram|Alpha //martin-thoma.com/cleverbot-vs-wolframalpha/ Fri, 23 Sep 2011 11:46:31 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/cleverbot-vs-wolframalpha <p><a href="http://cleverbot.com/" title="Cleverbot">Cleverbot</a> is an AI web application. You can chat with it and it tries to guess a good answer. This can be quite funny.</p> <p>I was curious how Cleverbot would answer when I compared it to <a href="http://www.wolframalpha.com/" title="answer engine">Wolfram|Alpha</a>, a useful answering engine.</p> <p>Here are two of my conversations:</p> <div style="width: 334px" class="wp-caption aligncenter"><a href="../images/2011/09/Cleverbot.png"><img src="../images/2011/09/Cleverbot.png" alt="Cleverbot" width="" height="" class="" /></a><p class="wp-caption-text">Cleverbot</p></div> <div style="width: 333px" class="wp-caption aligncenter"><a href="../images/2011/09/Cleverbot-2.png"><img src="../images/2011/09/Cleverbot-2.png" alt="Cleverbot" width="" height="" class="" /></a><p class="wp-caption-text">Cleverbot</p></div> <p>This Cleverbot isn’t very clever…</p> <p>Did you get some funny chats? Please post a link to a screenshot of your chat!</p> <p>edit: I just found this video. Too funny ☺</p> <iframe width="512" height="288" src="//www.youtube-nocookie.com/embed/WnzlbyTZsQY" frameborder="0" allowfullscreen=""></iframe> Getting Hardware Information in Ubuntu //martin-thoma.com/getting-hardware-information-in-ubuntu/ Thu, 22 Sep 2011 20:44:21 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/getting-hardware-information-in-ubuntu <p>I’m using Ubuntu now for many years, but I always have to look the commands for retrieving hardware information up. Now I will not Google any longer but search in my own little cheat sheet.</p> <p>I guess most commands will work in every Linux distribution, but I tried it only in Ubuntu 10.04LTS.</p> <p>Maybe you need to install some packages.</p> <p>If you know more commands, please post a comment!</p> <h2>CPU</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">cat /proc/cpuinfo processor : 0 vendor_id : GenuineIntel cpu family : 6 model : 23 model name : Pentium<span class="o">(</span>R<span class="o">)</span> Dual-Core CPU T4500 @ 2.30GHz stepping : 10 cpu MHz : 1200.000 cache size : <span class="m">1024</span> KB physical id : 0 siblings : 2 core id : 0 cpu cores : 2 apicid : 0 initial apicid : 0 fdiv_bug : no hlt_bug : no f00f_bug : no coma_bug : no fpu : yes fpu_exception : yes cpuid level : 13 wp : yes flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe nx lm constant_tsc arch_perfmon pebs bts aperfmperf pni dtes64 monitor ds_cpl est tm2 ssse3 cx16 xtpr pdcm xsave lahf_lm bogomips : 4588.23 clflush size : 64 cache_alignment : 64 address sizes : <span class="m">36</span> bits physical, <span class="m">48</span> bits virtual power management: processor : 1 vendor_id : GenuineIntel cpu family : 6 model : 23 model name : Pentium<span class="o">(</span>R<span class="o">)</span> Dual-Core CPU T4500 @ 2.30GHz stepping : 10 cpu MHz : 1200.000 cache size : <span class="m">1024</span> KB physical id : 0 siblings : 2 core id : 1 cpu cores : 2 apicid : 1 initial apicid : 1 fdiv_bug : no hlt_bug : no f00f_bug : no coma_bug : no fpu : yes fpu_exception : yes cpuid level : 13 wp : yes flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe nx lm constant_tsc arch_perfmon pebs bts aperfmperf pni dtes64 monitor ds_cpl est tm2 ssse3 cx16 xtpr pdcm xsave lahf_lm bogomips : 4588.44 clflush size : 64 cache_alignment : 64 address sizes : <span class="m">36</span> bits physical, <span class="m">48</span> bits virtual power management:</code></pre></div> <h2>RAM</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">free total used free shared buffers cached Mem: <span class="m">4047112</span> <span class="m">1712724</span> <span class="m">2334388</span> <span class="m">0</span> <span class="m">94328</span> 744808 -/+ buffers/cache: <span class="m">873588</span> 3173524 Swap: <span class="m">8864760</span> <span class="m">0</span> 8864760</code></pre></div> <h2>Graphic card</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci <span class="p">|</span> grep VGA 00:02.0 VGA compatible controller: Intel Corporation Mobile <span class="m">4</span> Series Chipset Integrated Graphics Controller <span class="o">(</span>rev 07<span class="o">)</span></code></pre></div> <p>And some more details:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci -s 00:02.0 -v 00:02.0 VGA compatible controller: Intel Corporation Mobile <span class="m">4</span> Series Chipset Integrated Graphics Controller <span class="o">(</span>rev 07<span class="o">)</span> Subsystem: Acer Incorporated <span class="o">[</span>ALI<span class="o">]</span> Device 048a Flags: bus master, fast devsel, latency 0, IRQ 29 Memory at d0000000 <span class="o">(</span>64-bit, non-prefetchable<span class="o">)</span> <span class="o">[</span><span class="nv">size</span><span class="o">=</span>4M<span class="o">]</span> Memory at c0000000 <span class="o">(</span>64-bit, prefetchable<span class="o">)</span> <span class="o">[</span><span class="nv">size</span><span class="o">=</span>256M<span class="o">]</span> I/O ports at <span class="m">4110</span> <span class="o">[</span><span class="nv">size</span><span class="o">=</span>8<span class="o">]</span> Capabilities: &lt;access denied&gt; Kernel driver in use: i915 Kernel modules: i915</code></pre></div> <h2>Audio Chipset</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci <span class="p">|</span> grep Audio 00:1b.0 Audio device: Intel Corporation 82801I <span class="o">(</span>ICH9 Family<span class="o">)</span> HD Audio Controller <span class="o">(</span>rev 03<span class="o">)</span></code></pre></div> <p>And some more details:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci -s 00:1b.0 -v 00:1b.0 Audio device: Intel Corporation 82801I <span class="o">(</span>ICH9 Family<span class="o">)</span> HD Audio Controller <span class="o">(</span>rev 03<span class="o">)</span> Subsystem: Acer Incorporated <span class="o">[</span>ALI<span class="o">]</span> Device 048a Flags: bus master, fast devsel, latency 0, IRQ 22 Memory at d6700000 <span class="o">(</span>64-bit, non-prefetchable<span class="o">)</span> <span class="o">[</span><span class="nv">size</span><span class="o">=</span>16K<span class="o">]</span> Capabilities: &lt;access denied&gt; Kernel driver in use: HDA Intel Kernel modules: snd-hda-intel</code></pre></div> <h2>Network Chipset</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci <span class="p">|</span> grep Network 04:00.0 Network controller: Atheros Communications Inc. AR9287 Wireless Network Adapter <span class="o">(</span>rev 01<span class="o">)</span></code></pre></div> <p>Then get some more information:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">lspci -s 04:00 -v 04:00.0 Network controller: Atheros Communications Inc. AR9287 Wireless Network Adapter <span class="o">(</span>rev 01<span class="o">)</span> Subsystem: Foxconn International, Inc. Device e034 Flags: bus master, fast devsel, latency 0, IRQ 17 Memory at d4600000 <span class="o">(</span>64-bit, non-prefetchable<span class="o">)</span> <span class="o">[</span><span class="nv">size</span><span class="o">=</span>64K<span class="o">]</span> Capabilities: &lt;access denied&gt; Kernel driver in use: ath9k Kernel modules: ath9k</code></pre></div> <h2>Monitor</h2> <p>The packages ddcprobe or xresprobe will help.</p> <h2>Hard disk</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">df -H Dateisystem Gr<span class="p">&amp;</span>ouml<span class="p">;&amp;</span>szlig<span class="p">;</span>e Benut Verf Ben% Eingeh<span class="p">&amp;</span>auml<span class="p">;</span>ngt auf /dev/sda1 307G 28G 264G 10% / none 2,1G 320k 2,1G 1% /dev none 2,1G 934k 2,1G 1% /dev/shm none 2,1G 209k 2,1G 1% /var/run none 2,1G <span class="m">0</span> 2,1G 0% /var/lock none 2,1G <span class="m">0</span> 2,1G 0% /lib/init/rw</code></pre></div> Benchmarking PHP //martin-thoma.com/benchmarking-php/ Thu, 22 Sep 2011 13:06:12 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/benchmarking-php <p>I used ApacheBenchmark (<a href="http://httpd.apache.org/docs/2.0/programs/ab.html" rel="nofollow">ab</a>) to make a few Benchmark tests I was interested in.</p> <p>If you like to view some more, go to <a href="http://www.phpbench.com/" rel="nofollow">www.phpbench.com</a>.</p> <p>The most important options are:</p> <ul> <li>-n: Number of requests to perform</li> <li>-c: Number of multiple requests to make</li> </ul> <p>An empty file:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">moose@pc07:~<span class="sb">`</span><span class="nv">$ </span>ab localhost/empty.php This is ApacheBench, Version 2.3 <span class="p">&amp;</span>amp<span class="p">;</span>lt<span class="p">;</span><span class="nv">$`</span>Revision: <span class="m">655654</span> <span class="sb">`</span><span class="nv">$&amp;</span>amp<span class="p">;</span>gt<span class="p">;</span> Copyright <span class="m">1996</span> Adam Twiss, Zeus Technology Ltd, http://www.zeustech.net/ Licensed to The Apache Software Foundation, http://www.apache.org/ Benchmarking localhost <span class="o">(</span>be patient<span class="o">)</span>.....done Server Software: Apache/2.2.14 Server Hostname: localhost Server Port: 80 Document Path: /empty.php Document Length: <span class="m">0</span> bytes Concurrency Level: 1 Time taken <span class="k">for</span> tests: 0.002 seconds Complete requests: 1 Failed requests: 0 Write errors: 0 Total transferred: <span class="m">210</span> bytes HTML transferred: <span class="m">0</span> bytes Requests per second: 461.04 <span class="o">[</span><span class="c">#/sec] (mean)</span> Time per request: 2.169 <span class="o">[</span>ms<span class="o">]</span> <span class="o">(</span>mean<span class="o">)</span> Time per request: 2.169 <span class="o">[</span>ms<span class="o">]</span> <span class="o">(</span>mean, across all concurrent requests<span class="o">)</span> Transfer rate: 94.55 <span class="o">[</span>Kbytes/sec<span class="o">]</span> received Connection Times <span class="o">(</span>ms<span class="o">)</span> min mean<span class="o">[</span>+/-sd<span class="o">]</span> median max Connect: <span class="m">0</span> <span class="m">0</span> 0.0 <span class="m">0</span> 0 Processing: <span class="m">2</span> <span class="m">2</span> 0.0 <span class="m">2</span> 2 Waiting: <span class="m">0</span> <span class="m">0</span> 0.0 <span class="m">0</span> 0 Total: <span class="m">2</span> <span class="m">2</span> 0.0 <span class="m">2</span> 2</code></pre></div> <p>Now I make 1000 requests to this empty file:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">ab -n <span class="m">1000</span> -c <span class="m">1</span> localhost/empty.php</code></pre></div> <p>Time per request: 1.158 [ms] (mean)</p> <p>With a document of two bytes, I get 1.324 ms. A HTML-Document with 300 kB has 4.287 ms.</p> <p>Now I’ll begin the test I’m interested in. It is related to <a href="http://stackoverflow.com/questions/4738605/undefined-offset-with-count" rel="nofollow">this Stackoverflow Question</a>. I’ll make 10000 requests per Benchmark:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">for</span>(<span style="color:#950">$i</span>=<span style="color:#00D">0</span>; <span style="color:#950">$i</span>&lt;<span style="color:#00D">5</span>; <span style="color:#950">$i</span>++) { <span style="color:#950">$maximum</span> = <span style="color:#369;font-weight:bold">max</span>( <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>]), <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">1</span>]), <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">2</span>]), <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">3</span>]), <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">4</span>]), <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">5</span>]), <span style="color:#C00;font-weight:bold">@</span><span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">6</span>]) ); <span style="color:#369;font-weight:bold">echo</span> <span style="color:#950">$maximum</span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20"> </span><span style="color:#710">'</span></span>; } </pre></div> </div> </div> <p>1.817 ms</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">for</span>(<span style="color:#950">$i</span>=<span style="color:#00D">0</span>; <span style="color:#950">$i</span>&lt;<span style="color:#00D">5</span>; <span style="color:#950">$i</span>++) { <span style="color:#950">$chunk</span> = <span style="color:#369;font-weight:bold">array_intersect_key</span>(<span style="color:#950">$MyArray</span>, <span style="color:#369;font-weight:bold">array</span>(<span style="color:#950">$i</span>*<span style="color:#00D">7</span>=&gt;<span style="color:#00D">1</span>, <span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">1</span>=&gt;<span style="color:#00D">2</span>, <span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">2</span>=&gt;<span style="color:#00D">3</span>, <span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">3</span>=&gt;<span style="color:#00D">4</span>, <span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">4</span>=&gt;<span style="color:#00D">5</span>, <span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#00D">5</span>=&gt;<span style="color:#00D">6</span>)); <span style="color:#080;font-weight:bold">if</span>(<span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$chunk</span>) &gt; <span style="color:#00D">0</span>){<span style="color:#950">$maximum</span> = <span style="color:#369;font-weight:bold">max</span>(<span style="color:#369;font-weight:bold">array_map</span>(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20">count</span><span style="color:#710">'</span></span>, <span style="color:#950">$chunk</span>));} <span style="color:#080;font-weight:bold">else</span> {<span style="color:#950">$maximum</span> = <span style="color:#00D">0</span>;} <span style="color:#369;font-weight:bold">echo</span> <span style="color:#950">$maximum</span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20"> </span><span style="color:#710">'</span></span>; } </pre></div> </div> </div> <p>1.801 ms</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#080;font-weight:bold">for</span>(<span style="color:#950">$i</span>=<span style="color:#00D">0</span>;<span style="color:#950">$i</span>&lt;<span style="color:#00D">5</span>;<span style="color:#950">$i</span>++){ <span style="color:#950">$arr</span> = <span style="color:#369;font-weight:bold">array</span>(); <span style="color:#080;font-weight:bold">for</span> (<span style="color:#950">$j</span>=<span style="color:#00D">0</span>;<span style="color:#950">$j</span>&lt;=<span style="color:#00D">6</span>;<span style="color:#950">$j</span>++) { <span style="color:#080;font-weight:bold">if</span> (<span style="color:#369;font-weight:bold">isset</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#950">$j</span>])) <span style="color:#950">$arr</span>[] = <span style="color:#369;font-weight:bold">count</span>(<span style="color:#950">$MyArray</span>[<span style="color:#950">$i</span>*<span style="color:#00D">7</span>+<span style="color:#950">$j</span>]); <span style="color:#080;font-weight:bold">else</span> {<span style="color:#950">$arr</span>[] = <span style="color:#00D">0</span>;} } <span style="color:#950">$maximum</span> = <span style="color:#369;font-weight:bold">max</span>(<span style="color:#950">$arr</span>); <span style="color:#369;font-weight:bold">echo</span> <span style="color:#950">$maximum</span>.<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">'</span><span style="color:#D20"> </span><span style="color:#710">'</span></span>; } </pre></div> </div> </div> <p>1.742 ms</p> Funny Commercials //martin-thoma.com/funny-commercials/ Wed, 21 Sep 2011 22:24:17 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/funny-commercials <p>Those commercials are so funny! I have never seen commercials which are that funny in TV. Did you? Although I know some good IKEA commercials, I have never heard of most of the other companies.</p> <p>Enjoy the clips!</p> <h2>Dirt Devil</h2> <iframe src="http://player.vimeo.com/video/22984504?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2> Berlitz</h2> <iframe width="512" height="414" src="http://www.youtube.com/embed/pMhICbFn2JI" frameborder="0" allowfullscreen=""></iframe> <h2> Nando's</h2> <iframe width="512" height="321" src="http://www.youtube.com/embed/jsqosiEyGLs" frameborder="0" allowfullscreen=""></iframe> <h2> IKEA - Tidy Up</h2> <iframe width="512" height="414" src="http://www.youtube.com/embed/WzMuax75s3M" frameborder="0" allowfullscreen=""></iframe> <h2> Ameriquest</h2> <iframe width="512" height="414" src="http://www.youtube.com/embed/QOixDP-SdKw" frameborder="0" allowfullscreen=""></iframe> <p>Don’t judge too fast!</p> <h2> Optician</h2> <iframe width="512" height="414" src="http://www.youtube.com/embed/RV6MZHRE3jU" frameborder="0" allowfullscreen=""></iframe> <h2> CPS</h2> <iframe width="512" height="321" src="http://www.youtube.com/embed/M_DCFHqVBIE" frameborder="0" allowfullscreen=""></iframe> <h2> Kellogs</h2> <iframe src="http://player.vimeo.com/video/8670278?title=0&amp;byline=0&amp;portrait=0" width="512" height="288" frameborder="0"></iframe> <h2> RWE</h2> <p>After a lot of criticism in Germany for beein environmental unfriendly because of operating nuclear power plants, RWE seems to have created this commercial:</p> <iframe src="http://player.vimeo.com/video/6209117?title=0&amp;byline=0&amp;portrait=0" width="512" height="290" frameborder="0"></iframe> <h2> Other Blogposts</h2> <ul> <li><a href="http://koikoikoi.com/2010/11/30-most-brilliant-and-creative-condom-ads/">30 Most Brilliant and Creative Condom Ads</a></li> </ul> Browser Wars //martin-thoma.com/browser-wars/ Wed, 21 Sep 2011 22:18:48 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/browser-wars <p>The Usage of different browser verions is very interesting for me. Internet Explorer 6 causes many problems in Webdesign as it doesn’t handle CSS and HTML as it should.</p> <p>This might be the reason why <a href="http://ie6update.com/">many</a> <a href="http://www.ie6nomore.com/">Webdesigners</a> <a href="http://wordpress.org/extend/plugins/stop-ie6/screenshots/">want</a> <a href="http://www.ie6death.com/">IE6</a> to <a href="http://www.bringdownie6.com/">die</a>.</p> <p>(Before I forget it: Thanks to <a href="http://www.flickr.com/photos/jeffmcneill/5883030204/sizes/o/in/photostream/" title="jeffmcneill">jeffmcneill</a> for sharing this image as CC BY-SA.)</p> <p>As Google has stopped to support Internet Explorer 6 I hope the decline of its usage will speed up.</p> <p>Here are two cool websites, that track browser versions:</p> <h2>IE6 Countdown</h2> <div style="width: 510px" class="wp-caption alignnone"><a href="../images/2011/09/ie6countdown.png"><img src="../images/2011/09/ie6countdown.png" alt="IE6 Countdown" width="" height="" class="size-full wp-image-691" /></a><p class="wp-caption-text"><a href="http://www.ie6countdown.com/">IE6 Countdown</a></p></div> <h2>Stat Counter</h2> <div id="browser_version-na-monthly-201002-201102" width="600" height="400" style="width:600px; height: 400px;"></div> <!-- You may change the values of width and height above to resize the chart --> <p>Source: <a href="http://gs.statcounter.com/#browser_version-na-monthly-201002-201102">StatCounter Global Stats - Browser Version Market Share</a></p> <script type="text/javascript" src="http://www.statcounter.com/js/FusionCharts.js"></script> <script type="text/javascript" src="http://gs.statcounter.com/chart.php?browser_version-na-monthly-201002-201102"></script> <h2>See also</h2> <ul> <li><a href="http://en.wikipedia.org/wiki/Browser_war">Browser Wars</a></li> <li><a href="http://en.wikipedia.org/wiki/Usage_share_of_web_browsers">Usage share of web browsers</a></li> <li><a href="http://en.wikipedia.org/wiki/Comparison_of_web_browsers">Comparison of web browsers</a></li> <li><a href="http://en.wikipedia.org/wiki/Mozilla_Firefox">Mozilla Firefox</a></li> <li><a href="http://en.wikipedia.org/wiki/Google_Chrome">Google Chrome</a></li> <li><a href="http://en.wikipedia.org/wiki/Opera_(web_browser)">Opera</a></li> </ul> Converting Files with Linux //martin-thoma.com/converting-files-with-linux/ Wed, 21 Sep 2011 22:10:08 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/converting-files-with-linux <p>The following tipps work under a Linux terminal and were tested with Ubuntu 10.04 LTS.</p> <p>I guess they will also work with other systems, as the programs are available for them.</p> <p>If you know some further file conversions, please let me know.</p> <p>I am also very interested in Web based conversions.</p> <h2 id="pdf">PDF</h2> <p>Convert a folder of PDF slides into text files of the same name. This is nice for using <code>grep</code>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ for file in *.pdf;do pdftotext &quot;$file&quot;; done </pre></div> </div> </div> <h2 id="image-files">Image Files</h2> <p>If you want to change image files via terminal, <a href="http://en.wikipedia.org/wiki/ImageMagick" rel="nofollow">ImageMagick</a> is a good choice.</p> <p><strong>Resize Images to a maximum resolution</strong></p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>convert &quot;OldPicture.jpg&quot; -resize 1600x1600 &quot;NewPicture.jpg&quot; </pre></div> </div> </div> <p>You can also do this for a whole folder. Just go into that folder and:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>for i in *.jpg; do convert $i -resize 1600x1600 $i; done </pre></div> </div> </div> <p>In case you have just taken many photos of a document and you want to send it as a single PDF via email. Thats the way to go:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>for i in *.JPG; do convert $i -resize 1200x1200 $i; done; convert *.JPG merged.pdf </pre></div> </div> </div> <p><strong>Create a Black-and-white picture and compress it</strong></p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ djpeg &quot;OldPicture.jpg&quot; | ppmtopgm | cjpeg -qual 70 &gt;&quot;NewPicture.jpg&quot; </pre></div> </div> </div> <p><b>Rename Pictures</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ rename -n &amp;rsquo;s/\.jpg$/\.JPG/&amp;rsquo; *.jpg </pre></div> </div> </div> <h2 id="audio-files">Audio Files</h2> <p><b>Give all mp3 songs the same sound level</b> (it’s called <a href="http://en.wikipedia.org/wiki/Audio_normalization" rel="nofollow">Audio normalization</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mp3gain -a *.mp3 </pre></div> </div> </div> <p><b>Merge many audio files to one</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mp3wrap merged.mp3 one.mp3 two.mp3 </pre></div> </div> </div> <p><b>Convert all *.wav-files in one folder two *.mp3-files and remove the *.wav-files</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ for i in *.wav;do lame &quot;$i&quot; &quot;${i%wav}mp3&quot;; rm &quot;$i&quot;; done </pre></div> </div> </div> <h2 id="video-files">Video Files</h2> <p>For quite a lot purposes is the command line tool <a href="http://en.wikipedia.org/wiki/FFmpeg" rel="nofollow">FFmpeg</a> with its <a href="http://www.ffmpeg.org/ffmpeg-doc.html">lots of options</a> a good choice. For others might <a href="http://en.wikipedia.org/wiki/MEncoder" rel="nofollow">MEncoder</a> be better. You might also want to install some codecs first:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ sudo apt-get install libavcodec-extra-52 libavdevice-extra-52 libavformat-extra-52 libavutil-extra-50 libpostproc-extra-51 libswscale-extra-0 libavcodec-unstripped-52 ubuntu-restricted-extras </pre></div> </div> </div> <p><b>Merge many video files to one</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ cat One.mpg Two.mpg Three.mpg | ffmpeg -f mpeg -i - -vcodec copy -acodec copy &quot;Merged.mpg&quot; </pre></div> </div> </div> <p><b>avi2mpg</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ffmpeg -i &quot;Original.avi&quot; &quot;New.mpg&quot; </pre></div> </div> </div> <p><b>mp42mpg</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ffmpeg -i &quot;Original.mp4&quot; -target ntsc-vcd &quot;New.mpg&quot; </pre></div> </div> </div> <p><b>mp42mp3</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ffmpeg -i Original.mp4 -f mp3 -ab 192000 -vn New.mp3 </pre></div> </div> </div> <p><b>mod2avi</b>: ?</p> <p><b>mts2ogg</b> (<a href="https://en.wikipedia.org/wiki/.m2ts">MTS format info</a>):</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre> </pre></div> </div> </div> <p><b>vcd2avi</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mencoder vcd://2 -o &quot;New.avi&quot; -oac copy -ovc lavc -lavcopts vcodec=mpeg4:vbitrate=2000 </pre></div> </div> </div> <p><b>ogv2avi</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mencoder &quot;Original.ogv&quot; -ovc xvid -oac mp3lame -xvidencopts pass=1 -o &quot;New.avi&quot; </pre></div> </div> </div> <p><b>wmv2mpg</b>: aspect=16/9 should eventually be changed to 4/3 or other aspects</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mencoder -of avi -ofps 25 \ -oac mp3lame -lameopts cbr:br=112:aq=3:mode=0:vol=0 \ -vf hqdn3d,softskip,harddup \ -ovc xvid \ -xvidencopts bitrate=501:max_key_interval=37:aspect=16/9:turbo:nochroma_me:notrellis:max_bframes=0:vhq=0 \ Original.wmv \ -o New.avi </pre></div> </div> </div> <p><b>mkv2avi</b>:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ mencoder &quot;Original.mkv&quot; -ovc lavc -lavcopts vcodec=mpeg4:vhq:vbitrate=6000 -oac mp3lame -lameopts vbr=3 -o &quot;New.avi&quot; </pre></div> </div> </div> <h3 id="converting-flash-videos-flv-to-mpg">Converting Flash Videos flv to mpg</h3> <p>You might want to get the information of the video first:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ffmpeg -i inputVideo.flv </pre></div> </div> </div> <p>This is how you convert it:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ffmpeg -i inputVideo.flv -acodec libmp3lame -ab 64k -s 320x240 -r 24 outputVideo.mpg </pre></div> </div> </div> <p><strong>-i</strong> input file <strong>-acodec</strong> audio codec <strong>-ab</strong> audio bitrate <strong>-s</strong> size <strong>-r</strong> fps where fps is the frame rate in Hz. The default value is 25Hz.</p> <h2 id="converting-flash-videos-flv-to-avi">Converting Flash Videos flv to avi</h2> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre>$ ffmpeg -i inputVideo.flv -sameq -ab 128k outputVideo.avi </pre></div> </div> </div> <h2 id="shortcuts-for-linux-console">Shortcuts for Linux Console</h2> <p>I convert svg2png or pdf2png quite often for my articles. So I’ve created a command.</p> <p>You can create a command in Linux very easy:</p> <ol> <li>Enter <code>echo $`PATH</code> in your console</li> <li>Go to <code>/usr/bin</code> or any other path in your PATH</li> <li>Create a file with the name of your command (e.g. svg2png)</li> <li>Fill the fill (see below for some examples).</li> <li>Make it executable: <code>chmod +x svg2png</code></li> </ol> <p>My <code>svg2png</code> looks like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">argparse</span> parser = argparse.ArgumentParser(description=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">convert a svg file to png</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-i</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--input</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">input</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">read svg file</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-o</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--output</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">output</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">output png file</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-w</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--width</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">width</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">512</span>, type=<span style="color:#369;font-weight:bold">int</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">width of output png</span><span style="color:#710">&quot;</span></span>) args = parser.parse_args() <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> command = <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">inkscape </span><span style="color:#710">&quot;</span></span> + args.input + \ <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> -w </span><span style="color:#710">&quot;</span></span> + <span style="color:#369;font-weight:bold">str</span>(args.width) + <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> --export-png=</span><span style="color:#710">&quot;</span></span> + args.output os.system(command) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Executed command: </span><span style="color:#710">&quot;</span></span> + command) </pre></div> </div> </div> <p>My pdf2png looks like this:</p> <div class="highlighter-coderay"><div class="CodeRay"> <div class="code"><pre><span style="color:#777">#!/usr/bin/env python</span> <span style="color:#777"># -*- coding: utf-8 -*-</span> <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">argparse</span> parser = argparse.ArgumentParser(description=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">convert a svg file to png</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-i</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--input</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">input</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">read svg file</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-o</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--output</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">output</span><span style="color:#710">&quot;</span></span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">output png file</span><span style="color:#710">&quot;</span></span>, metavar=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">FILE</span><span style="color:#710">&quot;</span></span>) parser.add_argument(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">-w</span><span style="color:#710">&quot;</span></span>, <span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">--width</span><span style="color:#710">&quot;</span></span>, dest=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">width</span><span style="color:#710">&quot;</span></span>, default=<span style="color:#00D">512</span>, type=<span style="color:#369;font-weight:bold">int</span>, help=<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">width of output png</span><span style="color:#710">&quot;</span></span>) args = parser.parse_args() <span style="color:#080;font-weight:bold">import</span> <span style="color:#B44;font-weight:bold">os</span> commands=[] commands.append(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">pdf2svg </span><span style="color:#710">&quot;</span></span>+args.input+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> ~</span><span style="color:#710">&quot;</span></span>+args.input+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">.svg</span><span style="color:#710">&quot;</span></span>) commands.append(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">inkscape ~</span><span style="color:#710">&quot;</span></span>+args.input+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">.svg --export-plain-svg=~</span><span style="color:#710">&quot;</span></span>+args.input+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">.svg</span><span style="color:#710">&quot;</span></span>) commands.append(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">svg2png -i ~</span><span style="color:#710">&quot;</span></span>+args.input+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">.svg -o </span><span style="color:#710">&quot;</span></span>+args.output+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20"> -w </span><span style="color:#710">&quot;</span></span> + <span style="color:#369;font-weight:bold">str</span>(args.width)) commands.append(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">rm ~</span><span style="color:#710">&quot;</span></span>+args.input+<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">.svg</span><span style="color:#710">&quot;</span></span>) <span style="color:#080;font-weight:bold">for</span> command <span style="color:#080;font-weight:bold">in</span> commands: os.system(command) print(<span style="background-color:hsla(0,100%,50%,0.05)"><span style="color:#710">&quot;</span><span style="color:#D20">Executed command: </span><span style="color:#710">&quot;</span></span> + command) args = parser.parse_args() </pre></div> </div> </div> Tricks with .htaccess //martin-thoma.com/tricks-with-htaccess/ Wed, 21 Sep 2011 22:02:59 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/tricks-with-htaccess <p>If your Website is running on an Apache2 Webserver, you can change the behaviour of this server with .htaccess-files.</p> <p>Here are some examples:</p> <h2> Enable htaccess-files</h2> <p>Set <a href="http://httpd.apache.org/docs/2.0/mod/core.html#allowoverride" rel="nofollow">AllowOverride</a> to “All”:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo gedit /etc/apache2/sites-available/default</code></pre></div> <p>Restart Apache:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo /etc/init.d/apache2 reload</code></pre></div> <h2> Enable ExpiresOn / mod_rewrite</h2> <p>This is for Ubuntu:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">sudo a2enmod rewrite expires sudo /etc/init.d/apache2 restart</code></pre></div> <h2> Prevent or allow directory listing</h2> <p>Add the following line to your .htaccess-file to allow directory listing:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Options +Indexes</code></pre></div> <p>Add the following line to your .htaccess-file to prevent directory listing:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">Options -Indexes</code></pre></div> <h2> Prevent Hot Linking</h2> <div class="highlight"><pre><code class="language-bash" data-lang="bash">RewriteEngine on RewriteCond %<span class="o">{</span>HTTP_REFERER<span class="o">}</span> !^<span class="sb">`</span><span class="err">$</span> RewriteCond %<span class="o">{</span>HTTP_REFERER<span class="o">}</span> !^http://<span class="o">(</span>www.<span class="o">)</span>?your-domain.com/.*<span class="nv">$`</span> <span class="o">[</span>NC<span class="o">]</span> RewriteRule <span class="se">\.</span><span class="o">(</span>gif<span class="p">|</span>jpe?g<span class="p">|</span>png<span class="o">)</span><span class="sb">`</span><span class="nv">$ </span>- <span class="o">[</span>F<span class="o">]</span></code></pre></div> <h2> Prevent Direct Access</h2> <p>If you include some files with PHP, you might want that others can’t access this file directly. So add the following to your .htaccess-file:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">&lt;FilesMatch <span class="s2">&quot;\.(inc)\.(php)$`&quot;</span>&gt; Order deny,allow Deny from all &lt;/FilesMatch&gt; &lt;FilesMatch <span class="s2">&quot;\.(tpl)$&quot;</span>&gt; Order deny,allow Deny from all &lt;/FilesMatch&gt;</code></pre></div> Ingenious Autocomplete //martin-thoma.com/ingenious-autocomplete/ Wed, 21 Sep 2011 21:48:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/ingenious-autocomplete <p>Did you notice some strange autocomplete-results? Keep in mind that Google gets those suggestions by other searches. They don’t employ someone who tries to guess what you mean. So many others have searched for the term which is suggested.</p> <p>Here are some I’ve tested: <strong>Some nations:</strong></p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-americans-are-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Autocomplete" src="../images/2011/09/autocomplete-americans-are.png" alt="Americans are ..." width="400" height="36" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-why-are-americans-so-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Why are Americans so ..." src="../images/2011/09/autocomplete-why-are-americans-so.png" alt="Why are Americans so ..." width="400" height="38" border="0" /></a></div> <p>If you really like to know, you should go to <a href="http://en.wikipedia.org/wiki/Obesity#Causes">wikipedia</a>. They have an article about <a href="http://en.wikipedia.org/wiki/Obesity_in_the_United_States">Obesity in the United States</a>. I thought obesity would be a serious problem <a href="http://en.wikipedia.org/wiki/Obesity_in_Germany">in Germany</a>, too. According to wikipedia, Germany is only on rank 43 of the fattest nations. You can even find an article called “<a href="http://en.wikipedia.org/wiki/Epidemiology_of_obesity">Epidemiology of obesity</a>”.</p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-canadians-a-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Canadians a..." src="../images/2011/09/autocomplete-canadians-a.png" alt="Canadians a..." width="400" height="39" border="0" /></a></div> <p>I’ve heard of this in <a href="http://en.wikipedia.org/wiki/How_i_met_your_mother">How I Met Your Mother</a>.</p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-germans-are-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Germans are ..." src="../images/2011/09/autocomplete-germans-are.png" alt="Germans are ..." width="400" height="81" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-germany-is-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Germany is ..." src="../images/2011/09/autocomplete-germany-is.png" alt="Germany is ..." width="400" height="74" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-why-are-germans-so-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Why are Germans so ..." src="../images/2011/09/autocomplete-why-are-germans-so.png" alt="Why are Germans so ..." width="400" height="78" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-england-is-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="England is ..." src="../images/2011/09/autocomplete-england-is.png" alt="England is ..." width="400" height="47" border="0" /></a></div> <p><strong>Some systems:</strong></p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-windows-is-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Windows is ..." src="../images/2011/09/autocomplete-windows-is.png" alt="Windows is ..." width="400" height="77" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-linux-is-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Linux is ..." src="../images/2011/09/autocomplete-linux-is.png" alt="Linux is ..." width="400" height="77" border="0" /></a></div> <p><a href="http://en.wikipedia.org/wiki/Apache_HTTP_Server">Apache</a> is one of the most common webservers.</p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-mac-is-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Mac is ..." src="../images/2011/09/autocomplete-mac-is.png" alt="Mac is ..." width="400" height="79" border="0" /></a></div> <p><strong>And many others:</strong></p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-can-je-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Can Jesus ..." src="../images/2011/09/autocomplete-can-je.png" alt="Can Jesus ..." width="400" height="82" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-can-you-get-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Can you get ..." src="../images/2011/09/autocomplete-can-you-get.png" alt="Can you get ..." width="400" height="79" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-chuck-norris-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Where ..." src="../images/2011/09/autocomplete-chuck-norris.png" alt="Where ..." width="400" height="77" border="0" /></a></div> <p>You don’t search for Chuck Norris, Chuck Norris finds you!</p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-facebook-is-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Facebook is ..." src="../images/2011/09/autocomplete-facebook-is.png" alt="Facebook is ..." width="400" height="76" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-google-is-big.png"><img style="border-style: initial; border-color: initial; border-width: 0px;" title="Google is ..." src="../images/2011/09autocomplete-google-is.png" alt="Google is ..." width="400" height="76" border="0" /></a></div> <p>I hope you have seen Terminator. Otherwise, you don’t know <a href="http://en.wikipedia.org/wiki/Skynet_(Terminator)">Skynet</a>.</p> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-if-i-ate-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="If I ate ..." src="../images/2011/09/autocomplete-if-i-ate.png" alt="If I ate ..." width="400" height="37" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-i-really-h-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="I really h ..." src="../images/2011/09/autocomplete-i-really-h.png" alt="I really h ..." width="400" height="49" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-is-it-wrong-to-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Is it wrong to ..." src="../images/2011/09/autocomplete-is-it-wrong-to.png" alt="Is it wrong to ..." width="400" height="76" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-is-there-a-big.png"><img src="../images/2011/09/autocomplete-is-there-a.png" alt="" width="400" height="66" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-steve-jobs-is-big.png"><img src="../images/2011/09/autocomplete-steve-jobs-is.png" alt="" width="400" height="50" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-where-do-i-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Why do I ..." src="../images/2011/09/autocomplete-where-do-i.png" alt="Why do I ..." width="400" height="73" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/autocomplete-why-is-my-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Why is my ..." src="../images/2011/09/autocomplete-why-is-my.png" alt="Why is my ..." width="400" height="80" border="0" /></a></div> <div class="separator" style="clear: both; text-align: center;"><a style="margin-left: 1em; margin-right: 1em;" href="../images/2011/09/google-religion-is-big.png"><img class="alignnone" style="border-style: initial; border-color: initial; border-width: 0px;" title="Religion is ..." src="../images/2011/09/google-religion-is.png" alt="Religion is ..." width="400" height="82" border="0" /></a></div> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Autocomplete-I-hate-it-when-i-300x61.png"><img src="../images/2011/09/Autocomplete-I-hate-it-when-i-300x61.png" alt="Google Autocomplete: I hate it when ..." width="" height="" class="size-medium wp-image-1681" /></a><p class="wp-caption-text">Google Autocomplete: I hate it when ...</p></div> Epic Translation Fails //martin-thoma.com/epic-translation-fails/ Wed, 21 Sep 2011 21:45:47 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/epic-translation-fails <p>Online translation programs are getting better and they are great if you want to get a vague idea of the content of a chinese website. Never the less you should know that the translations are not good enough by now:</p> <p>“Spielzeugladen” is German and means “toy store”</p> <div class="separator" style="clear: both; text-align: center;"> <img border="0" height="160" width="400" src="../images/2011/09/Google-Translator-Dirty-Picture.png" /></div> <p>Note the missing point.</p> <div class="separator" style="clear: both; text-align: center;"> <img border="0" height="193" width="400" src="../images/2011/09/Google-Translator-Was-hast-du-an.png" /></div> <p>“Was hast du an?” means “What do you wear?”</p> <div class="separator" style="clear: both; text-align: center;"> <img border="0" height="168" width="400" src="../images/2011/09/Google-Translator-Justin-Bieber-Puberty.png" /></div> <p>Did you know the Beatbox? Type “pv zk pv pv zk pv zk zk pv pv pv zk pv zk zk pzk pzk pvzkpkzvpvzk kkkkkk bsch”, translate from German to German and listen to it:</p> <iframe width="512" height="321" src="http://www.youtube.com/embed/KtjYKMtGNRc" frameborder="0" allowfullscreen=""></iframe> <p>Here you can listen to the translation-song:</p> <iframe width="512" height="321" src="http://www.youtube.com/embed/mqsrPNXEGdc" frameborder="0" allowfullscreen=""></iframe> 8 Animal Memes in Cyberculture //martin-thoma.com/8-animal-memes-in-cyberculture/ Wed, 21 Sep 2011 21:43:12 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/8-animal-memes-in-cyberculture <p>Animals are quite often in some web memes:</p> <h2>Lame Pun Coon</h2> <div style="width: 320px" class="wp-caption aligncenter"><a href="../images/2011/09/Lame-pun-coon.jpg"><img src="../images/2011/09/Lame-pun-coon.jpg" alt="Lame Pun Coon" width="" height="" class="size-full wp-image-1001" /></a><p class="wp-caption-text">Lame Pun Coon</p></div> <h2>Philosoraptor</h2> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Philosoraptor-300x300.jpg"><img src="../images/2011/09/Philosoraptor-300x300.jpg" alt="If he's a vegan since birth ... Does that mean he wasn't breast fed?" width="" height="" class="size-medium wp-image-381" /></a><p class="wp-caption-text">Philosoraptor</p></div> <h2>Lolcat</h2> <object width="512" height="341" classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" codebase="http://download.macromedia.com/pub/shockwave/cabs/flash/swflash.cab#version=6,0,40,0"><param name="flashvars" value="host=picasaweb.google.com&amp;hl=de&amp;feat=flashalbum&amp;RGB=0x000000&amp;feed=http%3A%2F%2Fpicasaweb.google.com%2Fdata%2Ffeed%2Fapi%2Fuser%2Fthemoosemind%2Falbumid%2F5444766564208572833%3Falt%3Drss%26kind%3Dphoto%26hl%3Dde" /><param name="pluginspage" value="http://www.macromedia.com/go/getflashplayer" /><param name="src" value="http://picasaweb.google.com/s/c/bin/slideshow.swf" /><embed width="512" height="341" type="application/x-shockwave-flash" src="http://picasaweb.google.com/s/c/bin/slideshow.swf" flashvars="host=picasaweb.google.com&amp;hl=de&amp;feat=flashalbum&amp;RGB=0x000000&amp;feed=http%3A%2F%2Fpicasaweb.google.com%2Fdata%2Ffeed%2Fapi%2Fuser%2Fthemoosemind%2Falbumid%2F5444766564208572833%3Falt%3Drss%26kind%3Dphoto%26hl%3Dde" pluginspage="http://www.macromedia.com/go/getflashplayer" /></object> <h2>Kung Fu Bear</h2> <div style="width: 330px" class="wp-caption alignnone"><a href="../images/2011/09/kungfu-bear.jpg"><img src="../images/2011/09/kungfu-bear.jpg" alt="Ize knowz kung fu!" width="" height="" class="size-medium wp-image-381" /></a><p class="wp-caption-text">Ize knowz kung fu!</p></div> <h2>Paranoid Parrot</h2> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Paranoid-Parrot-300x233.jpg"><img src="../images/2011/09/Paranoid-Parrot-300x233.jpg" alt="Paranoid Parrot" width="" height="" class="size-medium wp-image-411" /></a><p class="wp-caption-text">Paranoid Parrot</p></div> <h2>Socially Awkward Penguin</h2> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/Socially-Awkward-Penguin-300x300.jpg"><img src="../images/2011/09/Socially-Awkward-Penguin-300x300.jpg" alt="Socially Awkward Penguin" width="" height="" class="size-medium wp-image-421" /></a><p class="wp-caption-text">Socially Awkward Penguin</p></div> <h2>Bachelor Frog</h2> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/bachelor-frog-300x295.png"><img src="../images/2011/09/bachelor-frog-300x295.png" alt="Foul Bachelor Frog" width="" height="" class="size-medium wp-image-431" /></a><p class="wp-caption-text">Foul Bachelor Frog</p></div> <h2>Courage Wolf</h2> <div style="width: 310px" class="wp-caption alignnone"><a href="../images/2011/09/courage-wolf-vs-zombies-300x300.jpg"><img src="../images/2011/09/courage-wolf-vs-zombies-300x300.jpg" alt="Courage Wolf vs. Zombies" width="" height="" class="size-medium wp-image-441" /></a><p class="wp-caption-text">Courage Wolf vs. Zombies</p></div> <p>Do you know more? Do you know some better ones of the described ones? Please, post a comment!</p> Animater vs. Animation //martin-thoma.com/animater-vs-animation/ Wed, 21 Sep 2011 19:56:55 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/animater-vs-animation <p>An animator faces his own animation in deadly combat. The battlefield? The Flash interface itself. A stick figure is created by an animator with the intent to torture. The stick figure drawn by the animator will be using everything he can find - the brush tool, the eraser tool - to get back at his tormentor. It’s resourcefulness versus power. Who will win? You can find out yourself.</p> <iframe title="YouTube video player" width="512" height="414" src="http://www.youtube.com/embed/IF1heGQ3ttM" frameborder="0" allowfullscreen=""></iframe> <p>The Original Animator vs. Animation is from <a href="http://alanbecker.deviantart.com/art/Animator-vs-Animation-34244097">Alan Becker on Deviantart</a>.</p> 5 Online Comic Websites //martin-thoma.com/online-comic-websites/ Wed, 21 Sep 2011 19:53:03 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/online-comic-websites <p>All of those Websites offer one small comic strip each day. Some of them are a bit geeky, so you might not understand them if you don’t know anything about Linux / D&amp;D.</p> <h2>xkcd</h2> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2011/09/xkcd.png"><img src="../images/2011/09/xkcd.png" alt="xkcd" width="" height="" class="size-medium" /></a><p class="wp-caption-text"><a href="http://xkcd.com/">xkcd</a></p></div> <h2>hijinks ensue</h2> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2011/09/hijinksensue.png"><img src="../images/2011/09/hijinksensue.png" alt="hijinks ensue" width="" height="" class="size-medium" /></a><p class="wp-caption-text"><a href="http://hijinksensue.com/2011/01/11/failed-enterprises/" rel="nofollow">www.hijinksensue.com</a></p></div> <h2>Penny Arcade</h2> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2011/09/penny-arcade.png"><img src="../images/2011/09/penny-arcade.png" alt="Penny Arcade" width="" height="" class="size-medium" /></a><p class="wp-caption-text"><a href="http://www.penny-arcade.com/comic/2010/10/13/" rel="nofollow">www.penny-arcade.com/comic</a></p></div> <h2>The Perry Bible Fellowship Comics</h2> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2011/09/pbfcomics.png"><img src="../images/2011/09/pbfcomics.png" alt="The Perry Bible Fellowship Comics" width="" height="" class="size-medium" /></a><p class="wp-caption-text"><a href="http://www.pbfcomics.com/" rel="nofollow">www.pbfcomics.com</a></p></div> <h2>Realm of Atland</h2> <div style="width: 330px" class="wp-caption aligncenter"><a href="../images/2011/09/realm-of-atland.png"><img src="../images/2011/09/realm-of-atland.png" alt="Realm of Atland" width="" height="" class="size-medium" /></a><p class="wp-caption-text"><a href="http://www.realmofatland.com/?p=235" rel="nofollow">www.realmofatland.com</a></p></div> Freaky Wikipedia Articles //martin-thoma.com/freaky-wikipedia-articles/ Wed, 21 Sep 2011 19:44:21 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/freaky-wikipedia-articles <p>Wikipedia has <a href="http://en.wikipedia.org/wiki/Special:Statistics" rel="nofollow">a lot of articles</a> (&gt; 3.7 million). Sometimes, people have <a href="http://en.wikipedia.org/wiki/Wikipedia:Deleted_articles_with_freaky_titles" rel="nofollow">funny ideas for redirections / new articles</a>:</p> <p><a href="http://en.wikipedia.org/wiki/Wikipedia:Redirects_for_discussion/Log/2008_September_24#Pitbull_with_Lipstick_.E2.86.92_Sarah_Palin" rel="nofollow">Pitbull with Lipstick</a> - redirected to <a href="http://en.wikipedia.org/wiki/Sarah_Palin" rel="nofollow">Sarah Palin</a></p> <p>The belief that a cosmic jewish zombie who was his own father can make you live forever if you symbolically eat his flesh and telepathically tell him you accept him as your master, so he can remove an evil force from your soul that is present in humanity(<a href="http://en.wikipedia.org/w/index.php?title=Special:Log/delete&amp;page=The_belief_that_a_cosmic_jewish_zombie_who_was_his_own_father_can_make_you_live_forever_if_you_symbolically_eat_his_flesh_and_telepathically_tell_him_you_accept_him_as_your_master,_so_he_can_remove_an_evil_force_from_your_soul_that_is_present_in_humanity" rel="nofollow">Source</a>) - Was a Redirect to <a href="http://en.wikipedia.org/wiki/Christianity" rel="nofollow">Christianity</a></p> <p><a href="http://en.wikipedia.org/w/index.php?title=Special:Log&amp;type=delete&amp;user=&amp;page=22.86+Centimetre+Nails" rel="nofollow">22.86 Centimetre Nails</a> was a redirect to <a href="http://en.wikipedia.org/wiki/Nine_Inch_Nails" rel="nofollow">Nine Inch Nails</a>. Comment: Trent Reznor is not likely to go metric any time soon. :D</p> <p><a href="http://en.wikipedia.org/w/index.php?title=Special:Log&amp;type=delete&amp;user=&amp;page=Category:Recursive+categories" rel="nofollow">Recursive categories</a> - joke page which subcategoried itself</p> <p><a href="http://en.wikipedia.org/w/index.php?title=Special:Log&amp;type=delete&amp;user=&amp;page=Noooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooooo" rel="nofollow">Nooooooooooooooooooooooooooooooooooooooooooooooo[… 200 more …]ooooooo</a> - a redirect to <a href="http://en.wikipedia.org/wiki/Darth_Vader" rel="nofollow">Darth Vader</a></p> Setting up WordPress //martin-thoma.com/setting-up-wordpress/ Wed, 21 Sep 2011 19:36:18 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/setting-up-wordpress <p>This article is about creating a new WordPress blog. This includes installing and basic custominzation.</p> <p>You need to know how how to upload files and how your MySQL database credentials.</p> <p>I used almost the same setup and I will update this post if I make some bad experiences with it.</p> <h2>Requirements</h2> <h3>Minimum</h3> <p>Webserver with:</p> <ul> <li>MySQL 5.0 or higher</li> <li>PHP 5.2.4 or higher</li> <li>10 MB free space</li> <li>Any possibility to upload files</li> </ul> <h3>Recommended</h3> <ul> <li>The <a href="http://httpd.apache.org/docs/2.2/mod/mod_rewrite.html">mod_rewrite</a> Apache module.</li> <li>An FTP-Client (e.g. FileZilla)</li> </ul> <h2>Installation</h2> <ol> <li>Download the latest version from <a href="http://wordpress.org/download/">wordpress.org</a></li> <li>Decompress it and submit it to your Webserver. It should be directly in your working directory. <small>Example: Use www.martin-thoma.com, not www.martin-thoma.com/wordpress/</small></li> <li>Run the installation setup <ol> <li>Fill in your database information <small>(database name, host, database user, database password)</small></li> <li>Store <span class="inline-file">wp-config.php</span> in your WordPress-Folder.</li> <li>Make the most basic configuration of your blog <small>(give it a title, create the admin account)</small></li> </ol> </li> </ol> <h2>Plugins</h2> <ol> <ul> <li><a href="http://akismet.com/">Akismet</a>: Protect your blog from spam. Don't forget to add your API Key.</li> <li><a href="http://wordpress.org/extend/plugins/sociable">Sociable</a>: A little, customizable link bar with icons to share the post on social networks. I miss Google+ ☹</li> <li><a href="http://wordpress.org/extend/plugins/syntaxhighlighter/">SyntaxHighlighter Evolved</a>: A syntax highliter. Absolutely necessary, if you want to write about code. If you don't write about code, you don't need it.</li> <li><a href="http://wordpress.org/extend/plugins/twitter-tools/">Twitter Tools</a>: a plugin that creates a complete integration between your WordPress blog and your Twitter account.</li> <li><a href="http://wordpress.org/extend/plugins/wordpress-seo/">WordPress SEO by Yoast</a>: XML-Sitemap, binding for Google/Bing Webmaster Tools</li> <li><a href="http://wordpress.org/extend/plugins/wp-piwik/">WP-Piwik</a>: Piwik is an OpenSource alternative to Google Analytics. You can get some information about your readers. Download the latest Piwik-Version <a href="http://piwik.org/">here</a> and install it on your Website. Don't forget to add your Auth token.</li> </ul> </ol> <h2>Configuration</h2> <ol> <ol> <li>Add the categories you want. <small>Go to Posts &rarr; Categories</small></li> <li>Set your default category. <small>Go to Settings &rarr; Writing</small></li> <li>Delete the "Hello World!" post.</li> <li>Delete "Sample" page.</li> <li>Set a default category in Settings &rarr; Writing. Then delete the category "Uncategorized".</li> <li>Set up a custom theme. You can find free ones on <a href="http://wordpress.org/extend/themes">wordpress.org/extend/themes</a>.</li> <li>Use <a href="http://codex.wordpress.org/Using_Permalinks">Permalinks</a>. I use <span class="inline-code">/%postname%/</span> as I want short URLs. Another plus of this URL is that the URL never changes.</li> </ol> </ol> <h2>Finetuning</h2> <p><strong>www or non-www-URL</strong>: decide if you want www.martin-thoma.com or martin-thoma.com as your standard URL. Both should work, but one should redirect the user to the other. I choose to take martin-thoma.com as I like short URLs. Add this to your .htaccess if you want www.martin-thoma.com:</p> <div class="highlight"><pre><code class="language-bash" data-lang="bash">RewriteEngine on RewriteCond %<span class="o">{</span>HTTP_HOST<span class="o">}</span> !^www.martin-thoma.com<span class="sb">`</span><span class="err">$</span> RewriteRule ^<span class="o">(</span>.*<span class="o">)</span><span class="nv">$`</span> http://www.martin-thoma.com/<span class="nv">$1</span> <span class="o">[</span><span class="nv">R</span><span class="o">=</span>301<span class="o">]</span></code></pre></div> <p><strong>Imprint</strong>: In Germany, you have to create an imprint. Even if you don’t have to create one, I strongly recomment giving your readers the possibility to get to know who writes the posts. It gives you more credibility.</p> <h2>Piwik</h2> <ul> <li><a href="http://piwik.org/">Piwik</a></li> <li>Login &rarr; Geolocation tab &rarr; follow the instructions</li> </ul> <h2>Sources and further reading</h2> <ul> <li><a href="http://codex.wordpress.org/Using_Permalinks#Structure_Tags">Using Permalinks - Structure Tags.</a> Retrieved 17 September 2011.</li> <li><a href="http://www.jimwestergren.com/seo-for-wordpress-blogs/">SEO for WordPress &ndash; The Complete Guide.</a> Retrieved 17 September 2011.</li> </ul> Polyglots - Crazy Programming Stuff //martin-thoma.com/polyglots-crazy-programming-stuff/ Wed, 21 Sep 2011 19:28:02 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/polyglots-crazy-programming-stuff <p>Have you ever heard of polyglots? This is sooo crazy. A <a href="http://en.wikipedia.org/wiki/Polyglot_(computing)">polyglot</a> is a program which can be interpreded as many programming languages. You don’t believe me that something crazy like that is possible? Here is an example I’ve made:</p> <div class="highlight"><pre><code class="language-python" data-lang="python"><span class="c">#&gt;++++++++++[</span> <span class="c"># Python code written by Martin Thoma</span> <span class="c">#&gt;++++++++</span> <span class="c">#&gt;++++++++++</span> <span class="c"># Looping</span> <span class="c">#&gt;+++++++++++</span> <span class="k">def</span> <span class="nf">looping</span><span class="p">(</span><span class="n">i</span><span class="p">):</span> <span class="sd">&quot;&quot;&quot;&gt;++++++++++++ Do some crazy stuff x Written by Martin Thoma &quot;&quot;&quot;</span> <span class="n">answer</span> <span class="o">=</span> <span class="s">&quot;&quot;</span> <span class="k">while</span> <span class="n">i</span> <span class="o">%</span> <span class="mi">13</span> <span class="o">!=</span> <span class="mi">0</span><span class="p">:</span> <span class="k">if</span> <span class="n">i</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span> <span class="n">i</span> <span class="o">+=</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="k">elif</span> <span class="n">i</span> <span class="o">&gt;</span> <span class="mi">5</span><span class="p">:</span> <span class="n">i</span> <span class="o">+=</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="k">elif</span> <span class="n">i</span> <span class="o">&gt;</span> <span class="mi">10</span><span class="p">:</span> <span class="n">i</span> <span class="o">+=</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="k">elif</span> <span class="n">i</span> <span class="o">&gt;</span> <span class="mi">15</span><span class="p">:</span> <span class="n">i</span> <span class="o">+=</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="o">+</span> <span class="n">i</span> <span class="k">if</span> <span class="n">i</span> <span class="o">&gt;</span> <span class="mi">96</span><span class="p">:</span> <span class="sd">&quot;&quot;&quot;+++++++++++&quot;&quot;&quot;</span> <span class="k">if</span> <span class="n">i</span> <span class="o">&gt;</span> <span class="mi">122</span><span class="p">:</span> <span class="n">i</span> <span class="o">%=</span> <span class="mi">26</span> <span class="n">i</span> <span class="o">+=</span> <span class="mi">96</span> <span class="n">answer</span> <span class="o">=</span> <span class="n">answer</span><span class="o">+</span><span class="nb">chr</span><span class="p">(</span><span class="n">i</span><span class="p">)</span> <span class="sd">&quot;&quot;&quot;+++++++++&gt;++++++++++&gt;++++++++++++&gt;++++++++++&gt;++++++++++&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;+&gt;+++&gt;++++++++++&gt;+++++++++++&gt;++++++++++&gt;++++++++++&gt;+++&gt;++++++++++++&gt;++&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;++++++++&gt;++++++++++++&gt;+++&gt;++++++++++++&gt;+++++++++++&gt;+++++++++++&gt;+++++++&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;+++++&gt;++++++++++++&gt;++++++++++&gt;+++++++++++&gt;+++&gt;++++++++++&gt;++++++++++++&gt;&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;+++&gt;++++++++&gt;++++++++++&gt;+++++++++++&gt;++++++++++++&gt;+++++++++++&gt;+++++++++&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;++&gt;+++&gt;++++++++&gt;++++++++++&gt;+++++++++++&gt;+++++++++++&gt;++++++++++&gt;+++++&gt;++&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;+&gt;+++++++&gt;+++++++++++&gt;++++++++++&gt;++++++++++++&gt;++++++++++++&gt;++++&gt;+++&gt;++&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;++++++++&gt;++++++++++++&gt;++++++++++&gt;++++++&gt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;-]&gt;++++&gt;++++&gt;-----&gt;-----&gt;++&gt;----&gt;++++&gt;-&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;--&gt;-----&gt;&gt;++&gt;---&gt;-&gt;---&gt;++&gt;-&gt;+&gt;&gt;+&gt;++&gt;-&gt;---&gt;-----&gt;++&gt;-&gt;++++&gt;-----&gt;----&gt;-&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;---&gt;+&gt;&gt;++&gt;--&gt;+&gt;++&gt;---&gt;---&gt;++++&gt;----&gt;-----&gt;&gt;++&gt;++++&gt;++++&gt;+&gt;-&gt;---&gt;----&gt;+&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;+&gt;---&gt;++++&gt;---&gt;++&gt;+&gt;++++&gt;++&gt;++++&gt;---&gt;++++&gt;+++&gt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;.&gt;.&gt;. &gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&quot;&quot;&quot;</span> <span class="sd">&quot;&quot;&quot;&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&gt;.&quot;&quot;&quot;</span> <span class="k">return</span> <span class="n">answer</span> <span class="k">print</span> <span class="n">looping</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span> <span class="k">print</span><span class="p">(</span><span class="s">&quot;You&#39;ve just executed some Python-Code written by Martin Thoma&quot;</span><span class="p">)</span></code></pre></div> <p>You can download the file at <a href="../python/polyglot.py">martin-thoma.com/python/polyglot.py</a>.</p> <p>I used three languages in this piece of code: <a href="http://en.wikipedia.org/wiki/Python_(programming_language)">Python</a>, <a href="http://en.wikipedia.org/wiki/Brainfuck">Brainfuck</a> and <a href="http://en.wikipedia.org/wiki/Whitespace_(programming_language)">Whitespace</a>. You can try it with <a href="http://ideone.com/">ideone.com</a>. But please, copy the whole code!</p> <p>It might be considered as cheating to use comments as often as I did and using two esoteric programming languages. Whitespace works only with whitespaces (space, tab) and Brainfuck needs only +-.;&lt;&gt;[]. Everything else is interpreted as a comment.</p> <p>When I have much more freetime and I don’t know what to do, I’ll probably write some code with a more interesting output and which is not that obivous.</p> Imprint //martin-thoma.com/imprint/ Wed, 21 Sep 2011 18:36:59 +0200 info@martin-thoma.de (Martin Thoma) //martin-thoma.com/imprint <p>Martin Thoma<br /> Parkstraße 17<br /> 76131 Karlsruhe<br /></p> <p>mail: info@martin-thoma.de</p> <p>Verantwortlicher für die Inhalte des Angebots ist Martin Thoma.</p>